{"repo": "abdulawr/resume-enhancement-system", "files": {"src/main/java/com/basit/cz/completespringbootresumeenhancementsystem/controller/ResumeApiController.java": {"854a2a537fd1fb46b48f508ca16ea0df585add86": {"t": 1785745673.5557723, "n": 7169, "h": "6df5425c76dd23ee", "c": "package com.basit.cz.completespringbootresumeenhancementsystem.controller;\n\nimport com.basit.cz.completespringbootresumeenhancementsystem.config.DeepSeekConfig;\nimport com.basit.cz.completespringbootresumeenhancementsystem.dto.EnhancedResumeResponse;\nimport com.basit.cz.completespringbootresumeenhancementsystem.service.DeepSeekService;\nimport com.basit.cz.completespringbootresumeenhancementsystem.service.DocumentParserService;\nimport com.basit.cz.completespringbootresumeenhancementsystem.service.PdfGeneratorService;\nimport org.slf4j.Logger;\nimport org.slf4j.LoggerFactory;\nimport org.springframework.beans.factory.annotation.Autowired;\nimport org.springframework.http.HttpHeaders;\nimport org.springframework.http.HttpStatus;\nimport org.springframework.http.MediaType;\nimport org.springframework.http.ResponseEntity;\nimport org.springframework.web.bind.annotation.*;\nimport org.springframework.web.multipart.MultipartFile;\n\nimport java.io.IOException;\nimport java.util.HashMap;\nimport java.util.Map;\n\n@RestController\n@RequestMapping(\"/api/resume\")\npublic class ResumeApiController {\n\n private static final Logger logger = LoggerFactory.getLogger(ResumeApiController.class);\n\n @Autowired\n private DocumentParserService documentParserService;\n\n @Autowired\n private DeepSeekService deepSeekService;\n\n @Autowired\n private PdfGeneratorService pdfGeneratorService;\n\n @Autowired\n private DeepSeekConfig deepSeekConfig;\n\n @GetMapping(\"/config-status\")\n public ResponseEntity getConfigStatus() {\n Map status = new HashMap<>();\n\n try {\n boolean urlConfigured = deepSeekConfig.getUrl() != null && !deepSeekConfig.getUrl().isEmpty();\n boolean keyConfigured = deepSeekConfig.getKey() != null &&\n !deepSeekConfig.getKey().isEmpty() &&\n !deepSeekConfig.getKey().equals(\"sk-your-api-key-here\");\n boolean modelConfigured = deepSeekConfig.getModel() != null && !deepSeekConfig.getModel().isEmpty();\n\n status.put(\"url_configured\", urlConfigured);\n status.put(\"key_configured\", keyConfigured);\n status.put(\"model_configured\", modelConfigured);\n status.put(\"url\", urlConfigured ? deepSeekConfig.getUrl() : \"Not configured\");\n status.put(\"model\", modelConfigured ? deepSeekConfig.getModel() : \"Not configured\");\n status.put(\"key_status\", keyConfigured ? \"Configured\" : \"Missing or default value\");\n status.put(\"overall_status\", urlConfigured && keyConfigured && modelConfigured ? \"Ready\" : \"Configuration needed\");\n\n return ResponseEntity.ok(status);\n } catch (Exception e) {\n status.put(\"error\", e.getMessage());\n return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(status);\n }\n }\n\n @PostMapping(\"/enhance\")\n public ResponseEntity enhanceResume(\n @RequestParam(\"resume\") MultipartFile resumeFile,\n @RequestParam(\"jobDescription\") String jobDescription) {\n\n Map response = new HashMap<>();\n\n try {\n logger.info(\"Starting resume enhancement process\");\n\n // Check configuration first\n if (deepSeekConfig.getKey() == null || deepSeekConfig.getKey().isEmpty() ||\n deepSeekConfig.getKey().equals(\"sk-your-api-key-here\")) {\n response.put(\"success\", false);\n response.put(\"message\", \"DeepSeek API key is not configured. Please set the DEEPSEEK_API_KEY environment variable.\");\n return ResponseEntity.status(HttpStatus.SERVICE_UNAVAILABLE).body(response);\n }\n\n // Validate file\n if (!documentParserService.isValidResumeFile(resumeFile)) {\n response.put(\"success\", false);\n response.put(\"message\", \"Invalid file format. Please upload PDF, DOC, DOCX, or TXT files only.\");\n return ResponseEntity.badRequest().body(response);\n }\n\n // Extract text from resume\n logger.info(\"Extracting text from resume file: {}\", resumeFile.getOriginalFilename());\n String resumeText = documentParserService.extractTextFromFile(resumeFile);\n\n if (resumeText == null || resumeText.trim().isEmpty()) {\n response.put(\"success\", false);\n response.put(\"message\", \"Could not extract text from the resume file. Please ensure the file is not corrupted.\");\n return ResponseEntity.badRequest().body(response);\n }\n\n logger.info(\"Extracted {} characters from resume\", resumeText.length());\n\n // Enhance resume using DeepSeek\n logger.info(\"Sending resume to DeepSeek for enhancement\");\n EnhancedResumeResponse enhancedResume = deepSeekService.enhanceResume(resumeText, jobDescription);\n\n response.put(\"success\", true);\n response.put(\"data\", enhancedResume);\n logger.info(\"Resume enhancement completed successfully\");\n return ResponseEntity.ok(response);\n\n } catch (IOException e) {\n logger.error(\"Error processing resume file\", e);\n response.put(\"success\", false);\n response.put(\"message\", \"Error processing resume file: \" + e.getMessage());\n return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(response);\n } catch (IllegalStateException e) {\n logger.error(\"Configuration error\", e);\n response.put(\"success\", false);\n response.put(\"message\", \"Configuration error: \" + e.getMessage());\n return ResponseEntity.status(HttpStatus.SERVICE_UNAVAILABLE).body(response);\n } catch (Exception e) {\n logger.error(\"Unexpected error during resume enhancement\", e);\n response.put(\"success\", false);\n response.put(\"message\", \"Error enhancing resume: \" + e.getMessage());\n return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(response);\n }\n }\n\n @PostMapping(\"/generate-pdf\")\n public ResponseEntity generatePdfFromJson(@RequestBody EnhancedResumeResponse resumeData) {\n try {\n logger.info(\"Generating PDF from resume data\");\n byte[] pdfBytes = pdfGeneratorService.generateResumePdf(resumeData);\n\n HttpHeaders headers = new HttpHeaders();\n headers.setContentType(MediaType.APPLICATION_PDF);\n headers.setContentDispositionFormData(\"attachment\", \"enhanced_resume.pdf\");\n headers.setContentLength(pdfBytes.length);\n\n logger.info(\"PDF generated successfully, size: {} bytes\", pdfBytes.length);\n return new ResponseEntity<>(pdfBytes, headers, HttpStatus.OK);\n\n } catch (Exception e) {\n logger.error(\"Error generating PDF\", e);\n Map response = new HashMap<>();\n response.put(\"success\", false);\n response.put(\"message\", \"Error generating PDF: \" + e.getMessage());\n return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(response);\n }\n }\n}\n"}, "e2f036ac1e3350a9db7b9c7526ba36816f4a452e": {"t": 1785755636.2693985, "n": 7169, "h": "6df5425c76dd23ee", "c": "package com.basit.cz.completespringbootresumeenhancementsystem.controller;\n\nimport com.basit.cz.completespringbootresumeenhancementsystem.config.DeepSeekConfig;\nimport com.basit.cz.completespringbootresumeenhancementsystem.dto.EnhancedResumeResponse;\nimport com.basit.cz.completespringbootresumeenhancementsystem.service.DeepSeekService;\nimport com.basit.cz.completespringbootresumeenhancementsystem.service.DocumentParserService;\nimport com.basit.cz.completespringbootresumeenhancementsystem.service.PdfGeneratorService;\nimport org.slf4j.Logger;\nimport org.slf4j.LoggerFactory;\nimport org.springframework.beans.factory.annotation.Autowired;\nimport org.springframework.http.HttpHeaders;\nimport org.springframework.http.HttpStatus;\nimport org.springframework.http.MediaType;\nimport org.springframework.http.ResponseEntity;\nimport org.springframework.web.bind.annotation.*;\nimport org.springframework.web.multipart.MultipartFile;\n\nimport java.io.IOException;\nimport java.util.HashMap;\nimport java.util.Map;\n\n@RestController\n@RequestMapping(\"/api/resume\")\npublic class ResumeApiController {\n\n private static final Logger logger = LoggerFactory.getLogger(ResumeApiController.class);\n\n @Autowired\n private DocumentParserService documentParserService;\n\n @Autowired\n private DeepSeekService deepSeekService;\n\n @Autowired\n private PdfGeneratorService pdfGeneratorService;\n\n @Autowired\n private DeepSeekConfig deepSeekConfig;\n\n @GetMapping(\"/config-status\")\n public ResponseEntity getConfigStatus() {\n Map status = new HashMap<>();\n\n try {\n boolean urlConfigured = deepSeekConfig.getUrl() != null && !deepSeekConfig.getUrl().isEmpty();\n boolean keyConfigured = deepSeekConfig.getKey() != null &&\n !deepSeekConfig.getKey().isEmpty() &&\n !deepSeekConfig.getKey().equals(\"sk-your-api-key-here\");\n boolean modelConfigured = deepSeekConfig.getModel() != null && !deepSeekConfig.getModel().isEmpty();\n\n status.put(\"url_configured\", urlConfigured);\n status.put(\"key_configured\", keyConfigured);\n status.put(\"model_configured\", modelConfigured);\n status.put(\"url\", urlConfigured ? deepSeekConfig.getUrl() : \"Not configured\");\n status.put(\"model\", modelConfigured ? deepSeekConfig.getModel() : \"Not configured\");\n status.put(\"key_status\", keyConfigured ? \"Configured\" : \"Missing or default value\");\n status.put(\"overall_status\", urlConfigured && keyConfigured && modelConfigured ? \"Ready\" : \"Configuration needed\");\n\n return ResponseEntity.ok(status);\n } catch (Exception e) {\n status.put(\"error\", e.getMessage());\n return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(status);\n }\n }\n\n @PostMapping(\"/enhance\")\n public ResponseEntity enhanceResume(\n @RequestParam(\"resume\") MultipartFile resumeFile,\n @RequestParam(\"jobDescription\") String jobDescription) {\n\n Map response = new HashMap<>();\n\n try {\n logger.info(\"Starting resume enhancement process\");\n\n // Check configuration first\n if (deepSeekConfig.getKey() == null || deepSeekConfig.getKey().isEmpty() ||\n deepSeekConfig.getKey().equals(\"sk-your-api-key-here\")) {\n response.put(\"success\", false);\n response.put(\"message\", \"DeepSeek API key is not configured. Please set the DEEPSEEK_API_KEY environment variable.\");\n return ResponseEntity.status(HttpStatus.SERVICE_UNAVAILABLE).body(response);\n }\n\n // Validate file\n if (!documentParserService.isValidResumeFile(resumeFile)) {\n response.put(\"success\", false);\n response.put(\"message\", \"Invalid file format. Please upload PDF, DOC, DOCX, or TXT files only.\");\n return ResponseEntity.badRequest().body(response);\n }\n\n // Extract text from resume\n logger.info(\"Extracting text from resume file: {}\", resumeFile.getOriginalFilename());\n String resumeText = documentParserService.extractTextFromFile(resumeFile);\n\n if (resumeText == null || resumeText.trim().isEmpty()) {\n response.put(\"success\", false);\n response.put(\"message\", \"Could not extract text from the resume file. Please ensure the file is not corrupted.\");\n return ResponseEntity.badRequest().body(response);\n }\n\n logger.info(\"Extracted {} characters from resume\", resumeText.length());\n\n // Enhance resume using DeepSeek\n logger.info(\"Sending resume to DeepSeek for enhancement\");\n EnhancedResumeResponse enhancedResume = deepSeekService.enhanceResume(resumeText, jobDescription);\n\n response.put(\"success\", true);\n response.put(\"data\", enhancedResume);\n logger.info(\"Resume enhancement completed successfully\");\n return ResponseEntity.ok(response);\n\n } catch (IOException e) {\n logger.error(\"Error processing resume file\", e);\n response.put(\"success\", false);\n response.put(\"message\", \"Error processing resume file: \" + e.getMessage());\n return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(response);\n } catch (IllegalStateException e) {\n logger.error(\"Configuration error\", e);\n response.put(\"success\", false);\n response.put(\"message\", \"Configuration error: \" + e.getMessage());\n return ResponseEntity.status(HttpStatus.SERVICE_UNAVAILABLE).body(response);\n } catch (Exception e) {\n logger.error(\"Unexpected error during resume enhancement\", e);\n response.put(\"success\", false);\n response.put(\"message\", \"Error enhancing resume: \" + e.getMessage());\n return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(response);\n }\n }\n\n @PostMapping(\"/generate-pdf\")\n public ResponseEntity generatePdfFromJson(@RequestBody EnhancedResumeResponse resumeData) {\n try {\n logger.info(\"Generating PDF from resume data\");\n byte[] pdfBytes = pdfGeneratorService.generateResumePdf(resumeData);\n\n HttpHeaders headers = new HttpHeaders();\n headers.setContentType(MediaType.APPLICATION_PDF);\n headers.setContentDispositionFormData(\"attachment\", \"enhanced_resume.pdf\");\n headers.setContentLength(pdfBytes.length);\n\n logger.info(\"PDF generated successfully, size: {} bytes\", pdfBytes.length);\n return new ResponseEntity<>(pdfBytes, headers, HttpStatus.OK);\n\n } catch (Exception e) {\n logger.error(\"Error generating PDF\", e);\n Map response = new HashMap<>();\n response.put(\"success\", false);\n response.put(\"message\", \"Error generating PDF: \" + e.getMessage());\n return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(response);\n }\n }\n}\n"}}, "src/main/resources/application.properties": {"854a2a537fd1fb46b48f508ca16ea0df585add86": {"t": 1785746959.6824434, "n": 530, "h": "8dfdd58ee23d8d4f", "c": "spring.application.name=Resume Enhancement System\n\n\ndeepseek:\napi:\nurl:https://openrouter.ai/api/v1/chat/completions\nkey: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\ndeepseek.api.key=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\n\nmodel:deepseek/deepseek-r1-0528-qwen3-8b\n\nspring:\nservlet:\nmultipart:\nmax-file-size: 10MB\nmax-request-size: 10MB\nthymeleaf:\ncache: false\nprefix: classpath:/templates/\nsuffix: .html\n\nlogging:\nlevel:\ncom.resumeenhancer: DEBUG\n\nserver:\nport: 8080"}, "e2f036ac1e3350a9db7b9c7526ba36816f4a452e": {"t": 1785755636.6632228, "n": 530, "h": "8dfdd58ee23d8d4f", "c": "spring.application.name=Resume Enhancement System\n\n\ndeepseek:\napi:\nurl:https://openrouter.ai/api/v1/chat/completions\nkey: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\ndeepseek.api.key=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\n\nmodel:deepseek/deepseek-r1-0528-qwen3-8b\n\nspring:\nservlet:\nmultipart:\nmax-file-size: 10MB\nmax-request-size: 10MB\nthymeleaf:\ncache: false\nprefix: classpath:/templates/\nsuffix: .html\n\nlogging:\nlevel:\ncom.resumeenhancer: DEBUG\n\nserver:\nport: 8080"}}}}