{"record":{"id":"7eaec78b18b28817","repo":"srbhr/Resume-Matcher","slug":"failed-to-generate-outreach-message-please-try-ag","errorCode":null,"errorMessage":"Failed to generate outreach message. Please try again.","messagePattern":"Failed to generate outreach message\\. Please try again\\.","errorType":"http","errorClass":"HTTPException","httpStatus":500,"severity":"error","filePath":"apps/backend/app/routers/resumes.py","lineNumber":1898,"sourceCode":"    # Get resume data\n    resume_data = resume.get(\"processed_data\")\n    if not resume_data:\n        raise HTTPException(\n            status_code=400,\n            detail=\"Resume has no processed data. Please re-upload the resume.\",\n        )\n\n    # Get language setting\n    language = get_content_language()\n\n    # Generate outreach message\n    try:\n        outreach_content = await generate_outreach_message(\n            resume_data, job[\"content\"], language\n        )\n    except Exception as e:\n        logger.error(f\"Outreach message generation failed: {e}\")\n        raise HTTPException(\n            status_code=500,\n            detail=\"Failed to generate outreach message. Please try again.\",\n        )\n\n    # Save to resume record\n    await db.update_resume(resume_id, {\"outreach_message\": outreach_content})\n\n    return GenerateContentResponse(\n        content=outreach_content,\n        message=\"Outreach message generated successfully\",\n    )\n\n\n@router.post(\n    \"/{resume_id}/generate-interview-prep\",\n    response_model=GenerateInterviewPrepResponse,\n)\nasync def generate_interview_prep_endpoint(","sourceCodeStart":1880,"sourceCodeEnd":1916,"githubUrl":"https://github.com/srbhr/Resume-Matcher/blob/116f9cc3b00e1ac91734a6c2679bf41ea64a0edc/apps/backend/app/routers/resumes.py#L1880-L1916","documentation":"This 500 is raised by generate_outreach_endpoint when generate_outreach_message() throws any exception. The endpoint catches it, logs 'Outreach message generation failed', and returns a generic client-safe message while preserving the real cause in server logs.","triggerScenarios":"POSTing to the outreach route with valid resume/job context, but the AI helper fails — LLM API timeout, rate limiting, invalid API key, or resume/job content the model cannot handle.","commonSituations":"Missing/expired LLM provider credentials, upstream provider outage or 429s, oversized combined resume+job-description payload, blocked network egress.","solutions":["Check backend logs for 'Outreach message generation failed: <e>' to find the root cause","Validate the LLM API key and account quota in the backend environment","Retry — transient provider errors often succeed on a second attempt","Trim or truncate the resume/job description if the payload is too large"],"exampleFix":"// before\nawait generateOutreach(tailoredResume.id); // 500 generic\n// after\ntry {\n  await generateOutreach(tailoredResume.id);\n} catch (e) {\n  // check server logs for the underlying AI error, then retry\n}","handlingStrategy":"retry","validationCode":"const resume = await getResume(resumeId);\nconst improvement = await getImprovementByTailoredResume(resumeId);\nif (!resume?.processedData || !improvement?.jobId) throw new Error('Invalid inputs for outreach generation');","typeGuard":null,"tryCatchPattern":"try {\n  await api.generateOutreach(resumeId);\n} catch (e) {\n  if (e.response?.status === 500) {\n    // transient AI failure most likely: check server logs, then retry with backoff\n    await sleep(2000);\n    return api.generateOutreach(resumeId);\n  }\n  throw e;\n}","preventionTips":["Alert on 'Outreach message generation failed' log lines","Add retry-with-backoff around the LLM helper for 429/timeout errors","Keep the LLM API key valid and monitor quota usage","Cap combined resume+job prompt size to stay within model limits"],"tags":["http-500","ai-generation","backend"],"backgroundTag":"llm-generation-failed","analyzedSha":"116f9cc3b00e1ac91734a6c2679bf41ea64a0edc","analyzedAt":"2026-08-28T22:51:40.999Z","schemaVersion":2},"datasetVersion":"2026-08-29T02:17:18.158Z"}