a
    'Ni                     @   s*  d Z ddlZddlZddlZddlmZ dd Zdd Zdd	 Zd
d Zdd Z	dd Z
dd Zdd Zdd Zdd Zdd Zdd Zdd Zdd Zd d! Zd"d# Zd$d% Zd&d' Zd(d) Zd*d+ Zd,d- Zd.d/ ZdFd3d4ZdGd5d6Zd7d8 Zd9d: Zd;d< ZdHd>d?Z d@dA Z!dBdC Z"dDdE Z#dS )Ia  
Character Manager Module

This module contains all character creation and management functions for BaoLife.
Extracted from functions.py to improve code organization and maintainability.

Functions in this module handle:
- Character creation (players, NPCs, family members, friends, classmates, coworkers)
- Character data retrieval and manipulation
- Relationship management
- Avatar generation
- Bio and description generation
    N)	timedeltac                 C   s  | j  d| j d| j  d}| jD ]}|d| d7 }q&| jdkrt| drb|d| j d	7 }t| d
rt| jdr|d| jj	 d7 }| jdkrt| dr|d| j
 d7 }t| dr| jrt| jdr|d| jj	 d7 }| jdkrDt| dr| jr|dd| j 7 }t| drD| jrD|dd| j d7 }| jdkrt| d
r~t| jdr~|d| jj d7 }t| dr| jdkr|d| j d7 }|S ) z
    Generate a human-readable description of a person based on their attributes.

    Args:
        person: personClass instance

    Returns:
        str: Formatted description of the person
     z is a .z They are your z. r   ageYearsz
 They are 
 years oldjobtitlez, and work as a    	educationz They have a z level of educationcollegez, and graduated from (   likesz. Their interests include , dislikesz, but they dislike P   incomez. They earn approximately z per month from their jobmoneyz, and have about z in savings.)	firstnamelastnamesexlowerrelationshipsfamiliarityhasattrr   r   r   r
   r   r   joinr   r   r   persondescriptioni r   </var/www/lichun.app/lichun/ws/character/character_manager.pygetPersonDescription   s.    
 


r!   c                 C   s  d| j  d| j d| j  }| jD ]&}|dkr<|d7 }q&|d| d7 }q&t| drj|d	| j d
7 }t| drt| jdr|d| jj d7 }t| dr|d| j	  d7 }t| dr|d| j
 7 }t| dr| jrt| jdr|d| jj d7 }t| dr(| jr(|dd| j 7 }t| drT| jrT|dd| j d7 }t| drt| jdr|d| jj d7 }t| dr| jdkr|d| j d7 }|S ) z
    Generate an OpenAI-formatted description for AI conversation prompts.

    Args:
        person: personClass instance

    Returns:
        str: Formatted description for AI prompts
    zPretend you are r   z, a Zdating_matchz. Pretend you're on a dating app. You just met your conversation partner on a dating app. Be tastefuly flirty! If they are rude, you can end the conversation.z. You are a z to the conversation partnerr   z You're r   r   r   r   moodz and you are r
   z you studied r   z at r   z. you like r   r   z & dislike r   z. you earn z/mor   r   z & have z saved.)r   r   r   r   r   r   r   r   r   r"   r
   r   r   r   r   r   r   r   r   r   r    getOpenAIDescriptionC   s0    
 




r#   c                 C   sF  t | jdsd| j_t | jds(d| j_t | jds<d| j_ddg}ddg}g d	}d
}g d}g d}g d}d}g d}	d}
g d}g d}g d}g d}g d}g d}g d}g d}ddddddddddd dd!d"dd#d$dd%d&dd'd(dd)d*dd+d,dg
}g d-}g d.}g d/}d0}| jjdkrH|d17 }n|d2| jj 7 }| jjdkrr|d37 }n|d4| jj 7 }t | jdr| jjdkr|d57 }n|d6| jj 7 }|d7| jj 7 }|d8| jj 7 }|d9t| 7 }|d:t| 7 }|d;| jj	 7 }|d<| jj
 7 }|d=7 }|d>7 }|| _|S )?z
    Generate and set avatar URL for a person using DiceBear API.

    Args:
        person: personClass instance

    Returns:
        str: Avatar URL
    hairNONEfacial_hair	accessorytransparentZcircleincludeexclude)ZlongHairZ	shortHairZeyepatchZhatZhijabZturband   )blackZbluegrayZheatherpastelZpinkredZwhite)auburnr,   blondebrownr.   platinumr/   r-   )ZkurtZprescription01Zprescription02roundZ
sunglassesZ	wayfarers
   )mediumlightZmagesticZfancyZmagnum)r0   r,   r1   r2   r3   r/   )ZblazerZsweaterZshirtZhoodieZoverall)Z3c4f5cZ65c9ffZ262e33Z5199e4Z25557cZ929598Za7ffc4Zb1e2ffZe6e6e6Zff5c5cZff488eZffafb9Zffffb1Zffffff)
ZbatZbearZcumbiaZdeerZdiamondZholaZpizzaZresistZskullZskullOutline)angrydefaultZflatZraisedsadZunibrowZup)ZtannedZyellowZpaler7   r2   Z	darkBrownr,   )Z	concernedr9   Z	disbeliefr:   ZseriousZsmileZtwinkle)Z614335Zae5d29Zd08b5bZedb98aZf8d25cZfd9841Zffdbb4Black2c1b18namehex
Dark Brown4a312cChestnut Brown724133Auburna55728Golden Brownb58143Redc93305Blonded6b370
Light Greye8e1e1	Dark GreyecdcbfCopperf59797)r8   ZangryNaturalr9   ZdefaultNaturalZflatNaturalZfrownNaturalZraisedExcitedZraisedExcitedNaturalZsadConcernedZsadConcernedNaturalZunibrowNaturalZupDown)closedZcryr9   ZhappyZsideZsquintZ	surprised)
beardLightZbeardMajesticbeardMediumZmoustacheFancymoustacheMagnumz;https://api.dicebear.com/7.x/avataaars/svg?seed={person.id}z&topProbability=0z&top=z&facialHairProbability=0z&facialHair=z&accessoryProbability=0z&accessory=z&hairColor=z
&clothing=z&clothesColor=z&clothingGraphic=z&skinColor=z&mouth=z&eyes=defaultz&eyebrows=default)r   avatar_settingsr$   r&   r'   
hair_colorZclothingrandomchoice
skin_colorZmouthZimageURL)r   stylemodetopZ	topChanceZhatColorZ	hairColoraccessoriesZaccessoriesChanceZ
facialHairZfacialHairChanceZfacialHairColorZclothesZclothesColorZclothingGraphicZeyebrowZskinZmouthOptionsZ
skinColors
haircolorsZeyebrowsZeyesZfacial_hairsbase_urlr   r   r    
set_avatars   st    



ra   c                    sD  ddddddddddd	dd
dddddddddddddddddg
  fdd}t |  | jjdv r|d|d|d|dg}nX| jjdkr|d|d|dg}n4| jjdv r|d|dg}n|d|d
|dg}| jdkr:|d|v r||dgd  |d|v r:||dgd  t|S )z
    Get appropriate hair color based on person's age and skin tone.

    Args:
        person: personClass instance

    Returns:
        str: Hex color code for hair
    r;   r<   r=   r@   rA   rB   rC   rD   rE   rF   rG   rH   rI   rJ   rK   rL   rM   rN   rO   rP   rQ   c                    s&    D ]}|d | kr|d   S qd S )Nr>   r?   r   )Z
color_nameZcolorr_   r   r    get_hex   s    zget_hair_color.<locals>.get_hex)ZPALEZLIGHTZBROWN)Z
DARK_BROWNZBLACK2      )printrV   rZ   r   extendrX   rY   )r   rc   Zhair_colorsr   rb   r    get_hair_color   s4    rh   c                 C   s^   dg}| j dk rd}n:| j dkr4| jdkr4ddg}n| jdkrHg d}ng d}t|}|S )z
    Get appropriate hair type based on person's age and sex.

    Args:
        person: personClass instance

    Returns:
        str: Hair type identifier
    r%      rd   Malesides)ZdreadsZdreads01Zdreads02froZshaggyZshaggyMulletZ	shortFlatZ	theCaesarZtheCaesarAndSidePartZshavedSidesrk   Z
shortWavedZfrizzleZ
shortRoundZ
shortCurly)ZbigHairZbobZbunZcurlyrl   ZcurvyZfroBandZlongButNotTooLongZ
miaWallaceZ
straight01Z
straight02ZstraightAndStrand)r   r   rX   rY   )r   Z
hair_typesZ	hair_typer   r   r    get_hair_type  s    





rm   c                 C   s6   | j dkr.| jdkr.| jdkr.tg d}nd}|S )z
    Get appropriate facial hair based on person's age and sex.

    Args:
        person: personClass instance

    Returns:
        str: Facial hair type identifier
    rj      rd   )rS   rT   rU   r%   )r   r   rX   rY   )r   r&   r   r   r    get_facial_hair$  s    
ro   c                 C   s`   g d}| j dk rg d}n,d| j   kr2dkr@n n
g d}ng d}tj||ddd	 }|S )
z
    Get appropriate accessory (glasses) based on person's age.

    Args:
        person: personClass instance

    Returns:
        str: Accessory type identifier
    )r%   r4   r4   r4   rn   )g?x&?rp   rp   '   )g333333?/$?rr   rr   )g?皙?rs   rs   ri   )weightskr   )r   rX   choices)r   r^   Zprobsr'   r   r   r    get_accessory6  s    



rw   c                  C   s   ddl } | jdd dkr0g d}t|S ddlm} | }zJ| }|	d |
 }|d d  W |rz|  |  S |  n|r|  |  0 dS )	zd
    Get a random last name from the database.

    Returns:
        str: Capitalized last name
    r   NBAOLIFE_TEST_MODEfalsetrue)
ZSmithZJohnsonZWilliamsZBrownZJonesZGarciaZMillerZDavisZ	RodriguezZMartinezget_database_connectionzWSELECT name FROM lastnames_race WHERE lastnames_race.rank < 500 order by RAND() limit 1osenvirongetr   rX   rY   database.db_operationsr|   cursorZexecuteZfetchall
capitalizeclose)r~   Ztest_lastnamesr|   mydbmycursormyresultr   r   r    get_lastnameV  s*    

  
r   c           	      C   s   ddl }|jdd dkrB| dkr0g d}ng d}t|S dd	lm} | }zb| }d
}| dkrnd}d}|	||f |
 }|d d  W |r|  |  S |  n|r|  |  0 dS )z
    Get a random first name from the database based on gender.

    Args:
        gender: "Male" or "Female"

    Returns:
        str: Capitalized first name
    r   Nrx   ry   rz   Female)
ZEmmaZOliviaZAvaZIsabellaZSophiaZMiaZ	CharlotteZAmeliaZHarperZEvelyn)
ZLiamZNoahZOliverZElijahZJamesZWilliamZBenjaminZLucasZHenryZ	Alexanderr{   MFzWSELECT Name FROM firstnames WHERE Cnt > 1000000 AND Gender = %s ORDER BY RAND() LIMIT 1r}   )	Zgenderr~   Z
test_namesr|   r   r   ZgenderSelectorZsqlr   r   r   r    get_firstnamer  s6    


  
r   c                 C   sD   | j r@ddlm}m} ||jd}||| j d }|d| _dS )z
    Set a person's birthday based on their age in days and current date.

    Args:
        person: personClass instance
        player: playerClass instance
    r   )datetimer   z%m-%d)daysN)ageDaysr   r   strptimedatestrftimebirthday)r   playerr   r   Zcurrent_dater   r   r   r    setBirthday  s
    r   c                 C   s0  ddl m} | jd|  | jjdkrPd| jd _| jd   d| jd _n&d| jd _| jd   d| jd _| jd j	d t
| jd j| jd _t | jd _| jjtdd	 d
 | jd _| jd jd tdd | jd _| jd j| jd _t| | jd | jd< | jd j| j_| S )z
    Create a partner (boyfriend/girlfriend) for the player character.

    Args:
        player: playerClass instance

    Returns:
        playerClass: Updated player object
    r   personClassrj   r   Z
GirlfriendZ	Boyfriendpartnerri         m  )core.modelsr   rinsertcr   
setPronounr   r   appendr   r   r   r   r   rX   randintr   r   	setValuesidr   r   r   r   r   r    get_partner  s$    
 $r   c                 C   s   ddl m} | jd|  | jd jd | jd jd | jd jdkr^d| jd _nd| jd _d| jd _t	| jd j| jd _
| jj| jd _d| jd _d| jd _t| | jd | jd< | jd S )	z
    Create a child for the player character.

    Args:
        player: playerClass instance

    Returns:
        personClass: The newly created child
    r   r   childfamilyrj   ZSonZDaughterri   )r   r   r   r   r   r   r   r   familyLevelr   r   r   r   r   r   r   r   r   r   r    	add_child  s    
r   c                 C   s<   d}| j D ],}d|jv r
|s"|}q
|r
|j|jk r
|}q
|S )z
    Get the youngest child from player's relationships.

    Args:
        player: playerClass instance

    Returns:
        personClass or False: The youngest child or False if no children
    Fr   )r   r   r   )r   Zyoungestr   r   r   r    get_youngestChild  s    


r   c                 C   s  ddl m}m} ddlm}m} | }d|_|  |j	d |j	d d|_
d|_t|j|_| jj|_| jjtd	d
 |_|jd tdd |_| jjj|j_t| |}| jd| | }d|_|  |j	d |j	d d|_
d|_t|j|_| jj|_| jjtd	d
 |_|jd tdd |_| jjj|j_t| |}| jd| ||j|j| dd}|j|_|j|_|ddd |_|ddd |_| j	| | S )z
    Create mother and father for the player character.

    Args:
        player: playerClass instance

    Returns:
        playerClass: Updated player object
    r   r   relationshipClass)generate_random_daterandrj   fatherr   Fatherri   rn   "   r   r   motherMotherMarriedHappily married for years.rd   )r   r   r   utils.helpersr   r   r   r   r   r   r   r   r   r   r   r   r   rX   r   r   rV   rZ   r   r   r   r   relationshipaffinityrelData)r   r   r   r   r   r   r   Zparents_relationshipr   r   r    add_parents  sJ    




r   c                 C   s  ddl m} td tdddkrtd | }|jd |jd |jdkr^d	|_nd
|_d|_	t
|j|_|  | jj|_| jjtdd |_|jd d tdd |_| jjj|j_t| |}| jd| tdddkrtd | }|jd |jd |jdkr,d	|_nd
|_d|_	|  t
|j|_| jj|_| jd jtdd |_|jd d tdd |_| jjj|j_t| |}| jd| | S )z
    Create older siblings for the player character (with some randomness).

    Args:
        player: playerClass instance

    Returns:
        playerClass: Updated player object
    r   r   zadding older siblingsri   zadding older siblingsiblingr   rj   ZBrotherZSisterr   r     	   zadding another older sibling)r   r   rf   rX   r   r   r   r   r   r   r   r   r   r   r   r   r   rV   rZ   r   r   r   )r   r   r   r   r   r    add_older_siblings4  sJ    





r   c           	      C   s  ddl m}m} ddlm} | }d|_|  |jd |jd d|_	d|_
t|j|_| jj|_t| d	jtd
d |_|jd tdd |_| jjj|j_t| |}| jd| | }d|_|  |jd |jd d|_	d|_
t|j|_| jj|_t| d	jtd
d |_|jd tdd |_| jjj|j_t| |}| jd| ||j|j| dd}|j|_|j|_| j| | }d|_|  |jd |jd d|_	d|_
t|j|_t |_t| djtd
d |_|jd tdd |_| jjj|j_t| |}| jd| | }d|_|  |jd |jd d|_	d|_
t|j|_| jd j|_t| djtd
d |_|jd tdd |_| jjj|j_t| |}| jd| ||j|j| dd}|j|_|j|_| j| | S )z
    Create all four grandparents for the player character.

    Args:
        player: playerClass instance

    Returns:
        playerClass: Updated player object
    r   r   )r   r   Zpaternal_grandmotherr   ZGrandmotherre   r   rn   r   r   ri   rj   Zpaternal_grandfatherZGrandfatherr   r   Zmaternal_grandfatherr   Zmaternal_grandmother)r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   get_relationshipr   rX   r   r   rV   rZ   r   r   r   r   r   r   r   )	r   r   r   r   Zgrandmother1Zgrandfather1Zg_relZgrandfather2Zgrandmother2r   r   r    add_grandparentsl  s    






r   c                 C   s   ddl m} | }||_|  |jd d|_tdd|_	t
|j|_t |_|dkrt| jjtdd	 |_n^|d
kr| jjtdd d	 |_n:|dkr| jjtdd d	 |_n| jjtdd |_t| |}| jd| | S )z
    Create a friend for the player character.

    Args:
        player: playerClass instance
        sex: "Male" or "Female"
        age: "similar", "younger", "older", or other

    Returns:
        playerClass: Updated player object
    r   r   friendFriendF   r+   similarri   r   Zyoungerr   Zolder)r   r   r   r   r   r   r   rX   r   r   r   r   r   r   r   r   r   r   r   )r   r   ager   r   r   r   r    
add_friend  s&    
r   c                 C   s   g }t dt| jD ]$}d| j| jv r|| j|  qt|dkrt|  t dt| jD ]$}d| j| jv r^|| j|  q^|tdt|d  S )z
    Get a random classmate from player's relationships.
    Creates classmates if none exist.

    Args:
        player: playerClass instance

    Returns:
        personClass: A random classmate
    r   	classmateri   )rangelenr   r   r   create_classmatesrX   r   )r   Z
classmatesr   r   r   r    get_random_classmate  s    r   c                 C   sb   g }t dt| jD ]$}d| j| jv r|| j|  qt|dkrJdS |tdt|d  S )z
    Get a random friend from player's relationships.

    Args:
        player: playerClass instance

    Returns:
        personClass or False: A random friend or False if no friends
    r   r   Fri   )r   r   r   r   r   rX   r   )r   friendsr   r   r   r    get_random_friend  s    
r   c                 C   s   | j tdt| j d  S )z
    Get a random character from player's relationships.

    Args:
        player: playerClass instance

    Returns:
        personClass: A random character
    r   ri   )r   rX   r   r   )r   r   r   r    get_random_character  s    
r   c                 C   sb   g }t dt| jD ]$}| j| jdkr|| j|  qt|dkrJdS |tdt|d  S )z
    Get a random immediate family member (familyLevel == 1).

    Args:
        player: playerClass instance

    Returns:
        personClass: A random family member or None if no family
    r   ri   N)r   r   r   r   r   rX   r   r   r   r   r   r   r    get_random_family%  s    
r   c                 C   s>   g }t dt| jD ]$}| j| jdkr|| j|  q|S )z
    Get all immediate family members (familyLevel == 1).

    Args:
        player: playerClass instance

    Returns:
        list: List of all immediate family members
    r   ri   )r   r   r   r   r   r   r   r   r    get_allFamily8  s
    
r   rX   r   r   c                 C   s   ddl m} | }|dkr0|j| | |_|dkr>||_|  t|j|_	t
 |_|dkrz| jjtdd |_n6|dkrdtdd	 |_n|d
krdtdd |_|jd tdd |_t| |}|dkr|S | jd| | jd S dS )aW  
    Create a generic character with customizable attributes.

    Args:
        player: playerClass instance
        sex: "Male", "Female", or "random"
        age: "similar", "random_adults", "random_teens_adults", or other
        relationship: Relationship type or "none"

    Returns:
        personClass: The newly created character
    r   r   nonerX   r   ri   random_adultsrn   r   random_teens_adults   -   r   r   N)r   r   r   r   r   r   r   r   r   r   r   r   r   r   rX   r   r   r   r   r   )r   r   r   r   r   Znew_characterr   r   r    create_characterM  s,    

r   c                 C   s\   ddl m} |dkrXtddD ]}t| dd qt| ddd	}t|| jd
did |_dS )z
    Create 10 classmates and 1 teacher for the player.

    Args:
        player: playerClass instance
        activity: Optional activity parameter (unused currently)
    r   )find_where_testNr5   r   )r   Zteacherr   r   r   r   zElementary School Teacher)r   r   r   r   listoccupationsr   )r   activityr   r   r   r   r   r    r   ~  s    r   c                 C   sN   ddl m} td|ddD ]}t| ddd}||_qt| dd	d}||_d
S )z
    Create coworkers and a boss for the player.

    Args:
        player: playerClass instance
        occupation: Job occupation object
    r   r         Zcoworkerr   r   Zbossr   N)r   r   r   r   r   )r   
occupationr   r   r   r   r   r    create_coworkers  s    r   c                    s   t  fdd| jD dS )z
    Get a person by their ID from player's relationships.

    Args:
        player: playerClass instance
        id: Person's ID

    Returns:
        personClass or None: The person if found, None otherwise
    c                 3   s   | ]}|j  kr|V  qd S Nr   .0itemr   r   r    	<genexpr>      zget_person.<locals>.<genexpr>Nnextr   )r   r   r   r   r    
get_person  s    r   c                    s   t  fdd| jD dS )z
    Get a person by their relationship type.

    Args:
        player: playerClass instance
        type: Relationship type (e.g., "father", "mother", "friend")

    Returns:
        personClass or None: The person if found, None otherwise
    c                 3   s   | ]} |j v r|V  qd S r   )r   r   typer   r    r     r   z#get_relationship.<locals>.<genexpr>Nr   )r   r   r   r   r    r     s    r   Fc                 C   sV   t | jD ]F\}}t|jv r
| j| j| | j| j| |r
|| j| _q
| S )aC  
    Update a relationship type for all matching characters.

    Args:
        player: playerClass instance
        oldRelationship: Current relationship type
        newRelationship: New relationship type
        title: Optional new title for the relationship

    Returns:
        playerClass: Updated player object
    )	enumerater   r   r   remover   r   )r   ZoldRelationshipZnewRelationshipr   indexr   r   r   r    update_relationship  s    
r   c                 C   s  ddl m}m}m}m} ddlm} d}d}| jjdkr<d}| jjdkrLd	}| jj	||| | j_	| jj
||| | j_
|| j| _|| jj| j_| jj	d
krd
| j_	| jj
d
krd
| j_
| jj	dk r| jjd | j_| jj	dkr| jjd | j_|| | j || j | S )z
    Update player character's biological stats (hunger, thirst, weight).

    Args:
        player: playerClass instance

    Returns:
        playerClass: Updated player object
    r   )handleHungergetWeightTypehandleHealthhandleWeightr   re   ZUnderweightZObese   r+   g      ?b   )health.health_managerr   r   r   r   r   r   r   Z
weightTypeZhungerZthirstweight)r   r   r   r   r   r   r]   Zbottomr   r   r    	updateBio  s.    

r   c                 C   s   ddl m} ddlm} ddlm} ddlm} || | || || || | t||  t	||j
_t||j
_t||j
_t||j
_t||_|jdkrtdd|_|S )	z
    Set all default values for a character (education, job, avatar, etc.).

    Args:
        player: playerClass instance
        person: personClass instance

    Returns:
        personClass: Updated person object
    r   )setEducation)setLikesDislikes)	setHabits)	randomJobrn   r5   $   )Zeducation.education_managerr   Zstats.stats_managerr   r   r   Zjobs.job_managerr  r   rm   rV   r$   rh   rW   ro   r&   rw   r'   ra   imager   rX   r   actScore)r   r   r   r   r   r  r   r   r    r     s"    




r   c                 C   s  ddl m}m} ddlm} |d rZ|d d}|d | j_t|dkrR|d nd| j_	|d rtt
|d | j_nd	| j_| jjd
 | j_|d | j_d| j_| jjdkrd| j_nd| j_t| j| j_| jjst| jj| j_| jj	st | j_	| j|d| jj dd t| } t| } t| } t| | j| _d| _t| || jjd | jd jd || jj| jd j| jdd}|j| j_ |j| jd _ | j!| d| _"| S )z
    Set up the main player character with initial family and relationships.

    Args:
        player: playerClass instance
        data: Dictionary with 'name', 'age', 'sex' keys

    Returns:
        playerClass: Configured player object
    r   )locationClassr   )getOppositeSexr>   r   ri    r      r   r   r+   rj   ZHeZShehomezGhttps://cdn.midjourney.com/fe048fc6-f534-4ffe-9fb2-02297a3e1d2d/0_2.pngactiver   r   ZDatingzYou are dating!ZsetupComplete)#r   r  r   r   r  splitr   r   r   r   intr   r   r   r   Zpronounra   r  r   r   lr   r   r   r   r   r   
controllerr   r   r   r   r   r   status)r   datar  r   r  Z
name_partsrelr   r   r    characterSetup%  sD    


r  )rX   r   r   )N)F)$__doc__r   rX   uuidr   r!   r#   ra   rh   rm   ro   rw   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r  r   r   r   r    <module>   sF   )0d4 * 68['
1

$