o
    ;i                  
   @   s  d dl Z d dlZd dlmZmZmZmZ ejejd e	dZ
d dlmZmZmZ d dlmZ d dlmZmZ zd dlmZ W n! eya   d dlZeje je je d dlmZ Y nw G d	d
 d
eZG dd deZG dd deZG dd deZ G dd deZ!G dd deZ"G dd deZ#G dd deZ$eddddZ%e%j&edgddgdgd e%j'd e$d!d"e fd#d$Z(dS )%    N)DictListAnyOptional)levelskill_assessment_api)FastAPIHTTPExceptionstatus)CORSMiddleware)	BaseModelField)generate_skill_assessmentc                   @   s>   e Zd ZU dZee ed< dZee ed< dZee ed< dS )UserDetailsNskill_gap_namezSenior Software Engineerdesignation_namezSoftware Engineerjob_profile_name)	__name__
__module____qualname__r   r   str__annotations__r   r    r   r   P/var/www/eduai.edurigo.com/skill_assessment/testing/skill_assessment_fast_api.pyr      s   
 r   c                   @   s  e Zd ZU dZdZee ed< dZee ed< dZ	ee ed< dZ
ee ed< eed< dZee ed< dZee ed	< dZee ed
< dZee ed< dZee ed< dZee ed< dZee ed< dZee ed< dZee ed< dZee ed< dZee ed< dZee ed< dS )PreviouslyGeneratedQuestiona  
    Represents a single question that was already generated for the same
    skill and difficulty level in a previous attempt.  Only `question_name`
    is strictly required by the processor; all other fields are stored for
    reference and forwarded as-is.
    N%lms_user_skill_assessment_question_id	Client_Iduser_idlms_user_skill_assessment_idquestion_namequestion_typeoption_1option_2option_3option_4correct_answeruser_answerskill_id
skill_typeattempt
created_at
created_by)r   r   r   __doc__r   r   r   r   r   r   r   r    r!   r"   r#   r$   r%   r&   r'   r(   r)   r*   r+   r   r   r   r   r      s&   
 r   c                   @   s   e Zd ZU eed< eed< dS )SkillLevelObjidnameN)r   r   r   intr   r   r   r   r   r   r-   6   s   
 r-   c                   @   sz   e Zd ZU eed< eed< eddddZeed< eddddZ	eed< ee
d	d
Zee ed< ee
dd
Zee ed< dS )SkillAssessmentRequestuserDetailscompanyName   z_Difficulty level ID for the 3 questions to generate. Corresponds to the ID in the skills array.)defaultgedescriptionquestions_difficulty_levelzWhich attempt for this difficulty level (1-based). Increments each time the user retakes the same difficulty tier, ensuring fresh questions are generated on every retry.r)   z`Dynamic list of skill levels to map the questions_difficulty_level ID to its corresponding name.)default_factoryr7   skillszAll questions already generated for the *same* difficulty level across prior attempts.  Pass an empty list for attempt 1. The processor uses these to guarantee no repeated questions.previously_generated_questionsN)r   r   r   r   r   r   r   r8   r0   r)   listr:   r   r-   r;   r   r   r   r   r   r1   ;   s*   
 	
r1   c                   @   s&   e Zd ZU eed< eed< eed< dS )SkillOptionoptionId
optionText	isCorrectN)r   r   r   r   r   boolr   r   r   r   r=   d   s   
 r=   c                   @   s.   e Zd ZU eed< eed< eed< eed< dS )	SkillDataskillId	skillName
skillLevelr)   N)r   r   r   r   r   r0   r   r   r   r   rB   j   s
   
 rB   c                   @   sF   e Zd ZU eed< eed< eed< eed< ee ed< ee ed< dS )AssessmentQuestion
questionIdquestionText
difficultyquestionTyper:   optionsN)	r   r   r   r   r   r0   r   rB   r=   r   r   r   r   rF   q   s   
 rF   c                   @   s2   e Zd ZU eed< eed< eed< ee ed< dS )SkillAssessmentResponseassessmentIdassessmentTitletotalQuestions	questionsN)r   r   r   r   r   r0   r   rF   r   r   r   r   rL   z   s
   
 rL   zSkill Assessment APIa  Skill Assessment question generation powered by Ollama.

The `/skill_assessment_data` endpoint generates **exactly 3 questions** per call, scoped to a single difficulty level and attempt number, with built-in deduplication against previously generated questions.z2.0.0)titler7   version*T)allow_originsallow_credentialsallow_methodsallow_headersz/skill_assessment_data)response_modelpayloadc                    s   d}| j D ]}|j| jkr|j} nqtd| j d| jj d| jj	 d| d| j d| j
 dt| j  d	d
 | jD }t| j | j| j| j
||d}d|v r]ttj|d d|S )u/  
    Generate **3 skill-assessment questions** for a specific difficulty level
    and attempt number.

    ### Difficulty levels
    | `questions_difficulty_level` | Label        |
    |------------------------------|--------------|
    | 1                            | Beginner     |
    | 2                            | Intermediate |
    | 3                            | Advanced     |

    ### Attempt logic
    - `attempt=1` with `previously_generated_questions=[]` → first set of 3 questions.
    - `attempt=2` with all attempt-1 questions in `previously_generated_questions`
      → a completely fresh set of 3, guaranteed not to repeat earlier questions.
    - Each subsequent attempt follows the same pattern.

    Powered by **Ollama (gemma3:12b)** — no external API calls, no API keys needed.
    BeginnerzSkillAssessment | company=z | role=z	 | skill=z | difficulty=z (level=z) | attempt=z | prev_questions=c                 S   s   g | ]}|  qS r   )dict).0qr   r   r   
<listcomp>   s    z2skill_assessment_data_endpoint.<locals>.<listcomp>)user_detailscompany_namer8   r)   r;   difficulty_labelerror)status_codedetail)r:   r.   r8   r/   loggerinfor3   r2   r   r   r)   lenr;   r   r[   r	   r
   HTTP_500_INTERNAL_SERVER_ERROR)rY   ra   sprev_questions_dictsresultr   r   r   skill_assessment_data_endpoint   sJ   


	rl   ))osloggingtypingr   r   r   r   basicConfigINFO	getLoggerre   fastapir   r	   r
   fastapi.middleware.corsr   pydanticr   r   skill_assessment_processorr   ImportErrorsyspathappenddirnameabspath__file__r   r   r-   r1   r=   rB   rF   rL   appadd_middlewarepostrl   r   r   r   r   <module>   sJ    
)		