
    ]Ei#                     6   d Z ddlZddlmc mZ ddlZddlZddl	m
Z
 ddlmZ ddlZej                  j                  d e e
e      j$                               ddlmZmZmZmZmZ  G d d      Z G d d	      Z G d
 d      Z G d d      Z G d d      Zy)uA   generate_ai_image.py의 순수 함수에 대한 단위 테스트.    N)Path)Any)
COST_TABLE	SCENARIOSload_env_keysload_resultssave_resultsc                       e Zd ZdeddfdZdeddfdZdeddfdZdeddfdZdeddfdZdeddfd	Z	deddfd
Z
deddfdZy)TestLoadEnvKeystmp_pathreturnNc                    |dz  }|j                  dd       t        |      }ddd}||k(  }|st        j                  d|fd	||f      d
t	        j
                         v st        j                  |      rt        j                  |      nd
t        j                  |      dz  }dd|iz  }t        t        j                  |            dx}}y)u.   KEY=VALUE 형식을 올바르게 파싱한다.	.env.keyszFOO=bar
BAZ=qux
utf-8encodingbarqux)FOOBAZ==z%(py0)s == %(py3)sresultpy0py3assert %(py5)spy5N

write_textr   
@pytest_ar_call_reprcompare@py_builtinslocals_should_repr_global_name	_safereprAssertionError_format_explanationselfr   env_filer   @py_assert2@py_assert1@py_format4@py_format6s           @/home/jay/workspace/tools/ai-image-gen/test_generate_ai_image.pytest_parse_key_valuez$TestLoadEnvKeys.test_parse_key_value   s    k)07Cx(!&u55v55555v5555555v555v55555555555    c                    |dz  }|j                  dd       t        |      }ddi}||k(  }|st        j                  d|fd||f      d	t	        j
                         v st        j                  |      rt        j                  |      nd	t        j                  |      d
z  }dd|iz  }t        t        j                  |            dx}}y)u5   export KEY=VALUE 형식을 올바르게 파싱한다.r   zexport MY_KEY=my_value
r   r   MY_KEYmy_valuer   r   r   r   r   r   Nr    r*   s           r1   test_parse_export_prefixz(TestLoadEnvKeys.test_parse_export_prefix#   s    k)6Ix("J//v/////v///////v///v///////////r3   c                    |dz  }|j                  dd       t        |      }ddi}||k(  }|st        j                  d|fd||f      d	t	        j
                         v st        j                  |      rt        j                  |      nd	t        j                  |      d
z  }dd|iz  }t        t        j                  |            dx}}y)u>   큰따옴표로 감싸진 값에서 따옴표를 제거한다.r   zAPI_KEY="secret123"
r   r   API_KEY	secret123r   r   r   r   r   r   Nr    r*   s           r1   test_strip_double_quotesz(TestLoadEnvKeys.test_strip_double_quotes,       k)3gFx(#[11v11111v1111111v111v11111111111r3   c                    |dz  }|j                  dd       t        |      }ddi}||k(  }|st        j                  d|fd||f      d	t	        j
                         v st        j                  |      rt        j                  |      nd	t        j                  |      d
z  }dd|iz  }t        t        j                  |            dx}}y)uA   작은따옴표로 감싸진 값에서 따옴표를 제거한다.r   zAPI_KEY='secret456'
r   r   r9   	secret456r   r   r   r   r   r   Nr    r*   s           r1   test_strip_single_quotesz(TestLoadEnvKeys.test_strip_single_quotes5   r<   r3   c                    |dz  }|j                  dd       t        |      }ddi}||k(  }|st        j                  d|fd||f      d	t	        j
                         v st        j                  |      rt        j                  |      nd	t        j                  |      d
z  }dd|iz  }t        t        j                  |            dx}}y)u   빈 줄을 무시한다.r   z

FOO=bar

r   r   r   r   r   r   r   r   r   r   Nr    r*   s           r1   test_ignore_empty_linesz'TestLoadEnvKeys.test_ignore_empty_lines>   s    k)-@x('v''''v''''''v'''v''''''''''r3   c                    |dz  }|j                  dd       t        |      }ddi}||k(  }|st        j                  d|fd||f      d	t	        j
                         v st        j                  |      rt        j                  |      nd	t        j                  |      d
z  }dd|iz  }t        t        j                  |            dx}}y)u.   # 로 시작하는 주석 줄을 무시한다.r   u8   # 이것은 주석입니다
FOO=bar
# 또 다른 주석
r   r   r   r   r   r   r   r   r   r   Nr    r*   s           r1   test_ignore_comment_linesz)TestLoadEnvKeys.test_ignore_comment_linesG   s    k)I 	 	

 x('v''''v''''''v'''v''''''''''r3   c                 p   |dz  }t        |      }i }||k(  }|st        j                  d|fd||f      dt        j                         v st        j
                  |      rt        j                  |      ndt        j                  |      dz  }dd|iz  }t        t        j                  |            dx}}y)	u>   존재하지 않는 파일에 대해 빈 dict를 반환한다.zdoes_not_exist.keysr   r   r   r   r   r   N)	r   r"   r#   r$   r%   r&   r'   r(   r)   r+   r   missing_filer   r-   r.   r/   r0   s           r1   &test_file_not_found_returns_empty_dictz6TestLoadEnvKeys.test_file_not_found_returns_empty_dictS   so    "77|,v|vvvr3   c                    d}|dz  }|j                  |d       t        |      }ddddd	d
}||k(  }|st        j                  d|fd||f      dt	        j
                         v st        j                  |      rt        j                  |      ndt        j                  |      dz  }dd|iz  }t        t        j                  |            dx}}y)uB   다양한 형식이 혼합된 파일을 올바르게 파싱한다.zm# comment

PLAIN=value1
QUOTED="value2"
SINGLE='value3'
export EXPORTED=value4
export EXPORT_QUOTED="value5"
r   r   r   value1value2value3value4value5)PLAINQUOTEDSINGLEEXPORTEDEXPORT_QUOTEDr   r   r   r   r   r   Nr    )	r+   r   contentr,   r   r-   r.   r/   r0   s	            r1   test_mixed_formatsz"TestLoadEnvKeys.test_mixed_formats[   s    . 	 k)Gg6x(  %
 	
v 
 
 	
 	
v 
 	
 	
 
6	
 	
   	
 	
 
	  	
 	
 
	
 	
 	
 	
 	
 	
 	
r3   )__name__
__module____qualname__r   r2   r7   r;   r?   rA   rC   rG   rT    r3   r1   r   r      s    6T 6d 60 0$ 02 2$ 22 2$ 2( ( (
($ 
(4 
(t  
4 
D 
r3   r   c                   <    e Zd ZdeddfdZdeddfdZdeddfdZy)TestLoadResultsr   r   Nc                 &   ddddddddg}|dz  }|j                  t        j                  |      d	
       t        |      }||k(  }|st	        j
                  d|fd||f      dt        j                         v st	        j                  |      rt	        j                  |      nddt        j                         v st	        j                  |      rt	        j                  |      nddz  }dd|iz  }t        t	        j                  |            d}y)u&   올바른 JSON 파일을 로드한다.gptAmedium)apiscenarioqualitygeminiBlowresults.jsonr   r   r   z%(py0)s == %(py2)sr   datar   py2assert %(py4)spy4N)r!   jsondumpsr   r"   r#   r$   r%   r&   r'   r(   r)   )r+   r   rg   results_filer   r.   @py_format3@py_format5s           r1   test_load_valid_jsonz$TestLoadResults.test_load_valid_jsonz   s     sx@#%@&
  .0

4 07Cl+~vvvr3   c                 p   |dz  }t        |      }g }||k(  }|st        j                  d|fd||f      dt        j                         v st        j
                  |      rt        j                  |      ndt        j                  |      dz  }dd|iz  }t        t        j                  |            dx}}y)	u>   존재하지 않는 파일에 대해 빈 list를 반환한다.re   r   r   r   r   r   r   N)	r   r"   r#   r$   r%   r&   r'   r(   r)   rE   s           r1   &test_file_not_found_returns_empty_listz6TestLoadResults.test_file_not_found_returns_empty_list   sn    .0l+v|vvvr3   c                    |dz  }|j                  dd       t        |      }g }||k(  }|st        j                  d|fd||f      dt	        j
                         v st        j                  |      rt        j                  |      ndt        j                  |      dz  }d	d
|iz  }t        t        j                  |            dx}}y)u    빈 배열 JSON을 로드한다.re   z[]r   r   r   r   r   r   r   r   N)
r!   r   r"   r#   r$   r%   r&   r'   r(   r)   )r+   r   rn   r   r-   r.   r/   r0   s           r1   test_load_empty_listz$TestLoadResults.test_load_empty_list   s    .0w7l+v|vvvr3   )rU   rV   rW   r   rq   rs   ru   rX   r3   r1   rZ   rZ   y   s;    T d t  T d r3   rZ   c                   \    e Zd ZdeddfdZdeddfdZdeddfdZdeddfdZdeddfdZy)	TestSaveResultsr   r   Nc                    ddddddg}|dz  }t        ||       t        |      }||k(  }|st        j                  d|fd	||f      d
t	        j
                         v st        j                  |      rt        j                  |      nd
dt	        j
                         v st        j                  |      rt        j                  |      nddz  }dd|iz  }t        t        j                  |            d}y)uI   저장한 데이터를 다시 읽으면 동일한 내용이어야 한다.r\   r]   highK7A`?N)r_   r`   ra   cost_usderrorre   r   rf   reloadedrg   rh   rj   rk   
r	   r   r"   r#   r$   r%   r&   r'   r(   r)   )r+   r   rg   rn   r}   r.   ro   rp   s           r1   test_save_and_reloadz$TestSaveResults.test_save_and_reload   s     !!&
  .0\4(-4x4xx44r3   c                 r   |dz  }t        |g        |j                  } |       }|sddt        j                         v st	        j
                  |      rt	        j                  |      ndt	        j                  |      t	        j                  |      dz  }t        t	        j                  |            dx}}y)u/   save_results 호출 후 파일이 생성된다.re   zAassert %(py4)s
{%(py4)s = %(py2)s
{%(py2)s = %(py0)s.exists
}()
}rn   )r   ri   rk   N)	r	   existsr$   r%   r"   r&   r'   r(   r)   )r+   r   rn   r.   @py_assert3rp   s         r1   test_save_creates_filez&TestSaveResults.test_save_creates_file   st    .0\2&""$"$$$$$$$$|$$$|$$$"$$$$$$$$$$r3   c                 L   ddig}|dz  }t        ||       t        |      }|d   d   }d}||k(  }|slt        j                  d|fd||f      t        j                  |      t        j                  |      dz  }dd	|iz  }	t        t        j                  |	            d
x}x}}y
)uF   한글 텍스트를 포함한 데이터를 손상 없이 저장한다.messageu   한글 텍스트 테스트re   r   r   )z%(py1)s == %(py4)s)py1rk   zassert %(py6)spy6N)r	   r   r"   r#   r'   r(   r)   )
r+   r   rg   rn   r}   @py_assert0r   r-   rp   @py_format7s
             r1   test_save_korean_textz%TestSaveResults.test_save_korean_text   s    '02N&O%P.0\4(-{9%E)EE%)EEEEE%)EEEE%EEE)EEEEEEEEr3   c                    ddig}|dz  }t        ||       |j                  d      }d}||v }|st        j                  d|fd||f      t        j                  |      dt        j                         v st        j                  |      rt        j                  |      ndd	z  }d
d|iz  }t        t        j                  |            dx}}y)uB   저장된 파일에 한글이 이스케이프 없이 저장된다.keyu   한글re   r   r   )in)z%(py1)s in %(py3)sraw_content)r   r   r   r   N)
r	   	read_textr"   r#   r'   r$   r%   r&   r(   r)   )	r+   r   rg   rn   r   r   r-   r/   r0   s	            r1   !test_save_uses_ensure_ascii_falsez1TestSaveResults.test_save_uses_ensure_ascii_false   s    ',h&7%8.0\4(",,g,>&x;&&&&x;&&&x&&&&&&;&&&;&&&&&&&r3   c                    |dz  }ddig}ddig}t        ||       t        ||       t        |      }||k(  }|st        j                  d|fd||f      dt	        j
                         v st        j                  |      rt        j                  |      nddt	        j
                         v st        j                  |      rt        j                  |      ndd	z  }d
d|iz  }t        t        j                  |            d}y)u   기존 파일을 덮어쓴다.re   oldTnewr   rf   r}   new_datarh   rj   rk   Nr~   )	r+   r   rn   old_datar   r}   r.   ro   rp   s	            r1   test_overwrite_existing_filez,TestSaveResults.test_overwrite_existing_file   s    .0+0$-+0$-\8,\8,-8####x8######x###x######8###8#######r3   )	rU   rV   rW   r   r   r   r   r   r   rX   r3   r1   rw   rw      sd     T  d  $%t % %Fd Ft F'$ '4 '
$T 
$d 
$r3   rw   c                   $    e Zd ZddZddZddZy)TestScenariosNc                 <   t        t              }d}||k(  }|st        j                  d|fd||f      dt	        j
                         v st        j                  t               rt        j                  t               nddt	        j
                         v st        j                  t              rt        j                  t              ndt        j                  |      t        j                  |      dz  }dd|iz  }t        t        j                  |            d	x}x}}y	)
u7   SCENARIOS dict에 3개의 시나리오가 존재한다.   r   )z0%(py3)s
{%(py3)s = %(py0)s(%(py1)s)
} == %(py6)slenr   r   r   r   r   zassert %(py8)spy8N)
r   r   r"   r#   r$   r%   r&   r'   r(   r)   )r+   r-   @py_assert5@py_assert4r   @py_format9s         r1   test_has_three_scenariosz&TestScenarios.test_has_three_scenarios   s    9~""~""""~""""""s"""s""""""9"""9"""~""""""""""r3   c           	         t         j                  } |       }t        |      }h d}||k(  }|s&t        j                  d|fd||f      dt        j                         v st        j                  t              rt        j                  t              nddt        j                         v st        j                  t               rt        j                  t               ndt        j                  |      t        j                  |      t        j                  |      t        j                  |      dz  }dd|iz  }t        t        j                  |            d	x}x}x}x}}y	)
u#   SCENARIOS의 키는 A, B, C 이다.>   r]   rc   Cr   zb%(py7)s
{%(py7)s = %(py0)s(%(py5)s
{%(py5)s = %(py3)s
{%(py3)s = %(py1)s.keys
}()
})
} == %(py10)ssetr   r   r   r   r   py7py10assert %(py12)spy12N)r   keysr   r"   r#   r$   r%   r&   r'   r(   r)   r+   r-   r   @py_assert6@py_assert9@py_assert8@py_format11@py_format13s           r1   test_scenario_keys_are_a_b_cz*TestScenarios.test_scenario_keys_are_a_b_c   s    >>7>#7s#$77$7777$777777s777s77777797779777>777#777$77777777777r3   c                 
   t        j                         D ]k  \  }}t        |t              }|s%t	        j
                  d| d      dz   dt        j                         v st	        j                  t              rt	        j                  t              nddt        j                         v st	        j                  |      rt	        j                  |      nddt        j                         v st	        j                  t              rt	        j                  t              ndt	        j                  |      dz  }t        t	        j                  |            d}t        |      }d	}||kD  }|st	        j                  d
|fd||f      dt        j                         v st	        j                  t              rt	        j                  t              nddt        j                         v st	        j                  |      rt	        j                  |      ndt	        j                  |      t	        j                  |      dz  }t	        j
                  d| d      dz   d|iz  }	t        t	        j                  |	            dx}x}}n y)u@   모든 시나리오 값은 비어 있지 않은 문자열이다.u   시나리오 u   의 값이 str이 아닙니다.7
>assert %(py4)s
{%(py4)s = %(py0)s(%(py1)s, %(py2)s)
}
isinstancevaluestrr   r   ri   rk   Nr   >)z/%(py3)s
{%(py3)s = %(py0)s(%(py1)s)
} > %(py6)sr   r   u   의 값이 비어 있습니다.z
>assert %(py8)sr   )r   itemsr   r   r"   _format_assertmsgr$   r%   r&   r'   r(   r)   r   r#   )
r+   r   r   r   rp   r-   r   r   r   r   s
             r1   %test_all_values_are_non_empty_stringsz3TestScenarios.test_all_values_are_non_empty_strings   s[   #//+ 	XJCeS)_)__]3%?^+_______:___:______e___e______S___S___)______u:WW:>WWW:WWWWWW3WWW3WWWWWWuWWWuWWW:WWWWWW]3%7V#WWWWWWWW	Xr3   r   N)rU   rV   rW   r   r   r   rX   r3   r1   r   r      s    #8Xr3   r   c                   4    e Zd ZddZddZddZddZddZy)TestCostTableNc           	         t         j                  } |       }t        |      }h d}||k(  }|s&t        j                  d|fd||f      dt        j                         v st        j                  t              rt        j                  t              nddt        j                         v st        j                  t               rt        j                  t               ndt        j                  |      t        j                  |      t        j                  |      t        j                  |      dz  }dd|iz  }t        t        j                  |            d	x}x}x}x}}y	)
u4   COST_TABLE에 low, medium, high 키가 존재한다.>   rd   ry   r^   r   r   r   r   r   r   r   N)r   r   r   r"   r#   r$   r%   r&   r'   r(   r)   r   s           r1   test_has_low_medium_highz&TestCostTable.test_has_low_medium_high   s    ??B?$Bs$%B)BB%)BBBBB%)BBBBBBBsBBBsBBBBBB:BBB:BBB?BBB$BBB%BBB)BBBBBBBBBr3   c                 &   t         d   }t        j                  }d} ||      }||k(  }|st        j                  d|fd||f      t        j
                  |      dt        j                         v st        j                  t              rt        j
                  t              ndt        j
                  |      t        j
                  |      t        j
                  |      dz  }dd|iz  }t        t        j                  |            d	x}x}x}x}}y	)
u   low 비용은 0.011이다.rd   gI+?r   zL%(py1)s == %(py9)s
{%(py9)s = %(py5)s
{%(py5)s = %(py3)s.approx
}(%(py7)s)
}pytestr   r   r   r   py9assert %(py11)spy11Nr   r   approxr"   r#   r'   r$   r%   r&   r(   r)   r+   r   r   r   r   r-   @py_format10@py_format12s           r1   test_low_costzTestCostTable.test_low_cost   s    % 8FMM8%8M%$88 $88888 $8888 888888F888F888M888%888$888888888r3   c                 &   t         d   }t        j                  }d} ||      }||k(  }|st        j                  d|fd||f      t        j
                  |      dt        j                         v st        j                  t              rt        j
                  t              ndt        j
                  |      t        j
                  |      t        j
                  |      dz  }dd|iz  }t        t        j                  |            d	x}x}x}x}}y	)
u   medium 비용은 0.042이다.r^   g/$?r   r   r   r   r   r   Nr   r   s           r1   test_medium_costzTestCostTable.test_medium_cost   s    (#;v}};U;}U';;#';;;;;#';;;;#;;;;;;v;;;v;;;};;;U;;;';;;;;;;;;r3   c                 &   t         d   }t        j                  }d} ||      }||k(  }|st        j                  d|fd||f      t        j
                  |      dt        j                         v st        j                  t              rt        j
                  t              ndt        j
                  |      t        j
                  |      t        j
                  |      dz  }dd|iz  }t        t        j                  |            d	x}x}x}x}}y	)
u   high 비용은 0.167이다.ry   rz   r   r   r   r   r   r   Nr   r   s           r1   test_high_costzTestCostTable.test_high_cost  s    &!9V]]959]5%99!%99999!%9999!999999V999V999]9995999%999999999r3   c                 0   t        j                         D ]  \  }}t        |t              }|s$t	        j
                  | d      dz   dt        j                         v st	        j                  t              rt	        j                  t              nddt        j                         v st	        j                  |      rt	        j                  |      nddt        j                         v st	        j                  t              rt	        j                  t              ndt	        j                  |      dz  }t        t	        j                  |            d}d}||kD  }|st	        j                  d	|fd
||f      dt        j                         v st	        j                  |      rt	        j                  |      ndt	        j                  |      dz  }t	        j
                  | d      dz   d|iz  }t        t	        j                  |            dx}} y)u(   모든 비용 값은 양수 float이다.u!    비용이 float이 아닙니다.r   r   costfloatr   Nr   r   )z%(py0)s > %(py3)sr   u    비용이 0 이하입니다.z
>assert %(py5)sr   )r   r   r   r   r"   r   r$   r%   r&   r'   r(   r)   r#   )	r+   ra   r   r   rp   r-   r.   r/   r0   s	            r1   "test_all_costs_are_positive_floatsz0TestCostTable.test_all_costs_are_positive_floats  s&   '--/ 	GMGTdE*Y*YYwi7X,YYYYYYY:YYY:YYYYYYdYYYdYYYYYYEYYYEYYY*YYYYYYF4!8FFF4!FFFFFF4FFF4FFF!FFFy(EFFFFFFFF	Gr3   r   )rU   rV   rW   r   r   r   r   r   rX   r3   r1   r   r      s    C9<:Gr3   r   )__doc__builtinsr$   _pytest.assertion.rewrite	assertionrewriter"   rl   syspathlibr   typingr   r   pathinsertr   __file__parentgenerate_ai_imager   r   r   r   r	   r   rZ   rw   r   r   rX   r3   r1   <module>r      s    G    
    3tH~,,- . X
 X
@ J9$ 9$BX X*G Gr3   