
    i9s              	          d Z ddlZddlmc mZ ddlZddl	Z	ddl
Z
ddlZddlmZ ddlmZ ddlZ ee
j                   j#                  dd            Zedz  dz  Zd	 Z e       Zd
ddddddg ddiddddddZ ej.                         d        Z ej.                         d        Z G d d      Z G d d      Z G d d      Z G d d       Z G d! d"      Z G d# d$      Z G d% d&      Z y)'u  
test_add_team.py

scripts/add-team.py 단위 테스트 (아르고스 작성)

테스트 항목:
- load_config(): teams.json 로드, 파일 없을 때 기본값 반환
- save_config(): 파일 저장, 메타데이터 자동 계산, updated 타임스탬프 설정
- generate_team_id(): 한글→영문 변환, 특수문자 제거, 소문자 처리
- create_team_directory(): 팀 디렉터리 및 기본 파일 생성
- add_team(): 팀 추가, 중복 검사, config 저장, 디렉터리 생성
- list_teams(): 팀 목록 출력, 빈 목록 메시지
- main(): CLI 인수 파싱, --list, --name/--type 필수 검사

격리: monkeypatch로 _mod.CONFIG_FILE 과 _mod.TEAMS_DIR 을 tmp_path로 교체
    N)datetime)PathWORKSPACE_ROOTz/home/jay/workspacescriptsadd-team.pyc                      t         j                  j                  dt              } t         j                  j	                  |       }| j
                  j                  |       |S )u/   add-team.py를 importlib로 로드하여 반환add_team)	importlibutilspec_from_file_location_SCRIPT_PATHmodule_from_specloaderexec_module)specmodules     */home/jay/workspace/tests/test_add_team.py_load_moduler   #   sC    >>11*lKD^^,,T2FKKF#M    1.0z2026-03-02 04:05:57	dev1-team
   개발1팀   수직조직activehermes)vulcanirisathenaargos)nametypestatusleadmembers      )total_teamsactive_teamsplanned_teamstotal_members)versionupdatedteamsmetadatac              #   (  K   | dz  }|j                          | dz  }|j                          |dz  }|j                  t        j                  t        dd      d       |j                  t        d	|       |j                  t        d
|       |  yw)uS   tmp_path에 config/teams.json을 생성하고 모듈 전역 변수를 패치한다.configr-   
teams.jsonF   ensure_asciiindentutf-8encodingCONFIG_FILE	TEAMS_DIRN)mkdir
write_textjsondumps_SAMPLE_CONFIGsetattr_mod)tmp_pathmonkeypatch
config_dir	teams_dirconfig_files        r   setup_configrG   F   s      H$J7"IOO|+K

>a@7   m[9k95
Ns   BBc              #   ,  K   | dz  }|j                          | dz  }|j                          |dz  }di i d}|j                  t        j                  |dd      d	
       |j	                  t
        d|       |j	                  t
        d|       |  yw)uU   빈 팀 목록을 가진 config를 생성하고 모듈 전역 변수를 패치한다.r0   r-   r1   r   r+   r-   r.   Fr2   r3   r6   r7   r9   r:   N)r;   r<   r=   r>   r@   rA   )rB   rC   rD   rE   rF   emptys         r   empty_configrK   Y   s      H$J7"IOO|+K;E

5uQ7'   m[9k95
Ns   BBc                   4    e Zd ZdZd Zd Zd Zd Zd Zd Z	y)	TestLoadConfigu   load_config() 함수 테스트c                 *   t         j                         }|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}}d	}|d
   }||v }|slt        j                  d|fd||f      t        j                  |      t        j                  |      dz  }dd|iz  }t        t        j                  |            dx}x}}y)u.   기존 teams.json을 올바르게 로드한다r+   r   ==z%(py1)s == %(py4)spy1py4assert %(py6)spy6Nr   r-   inz%(py1)s in %(py4)srA   load_config
@pytest_ar_call_reprcompare	_safereprAssertionError_format_explanationselfrG   r0   @py_assert0@py_assert3@py_assert2@py_format5@py_format7s           r   test_load_config_from_filez)TestLoadConfig.test_load_config_from_fileu   s    !!#i )E) E)))) E))) )))E)))))))-fWo-{o----{o---{---o-------r   c                    |dz  dz  }|j                  t        d|       t        j                         }di i 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=   파일이 존재하지 않을 때 기본 dict를 반환한다r0   r1   r9   r   rI   rO   z%(py0)s == %(py3)spy0py3assert %(py5)spy5N)r@   rA   r[   r\   r]   @py_builtinslocals_should_repr_global_namer^   r_   r`   )	rb   rB   rC   missingr0   re   @py_assert1@py_format4@py_format6s	            r   test_load_config_missing_filez,TestLoadConfig.test_load_config_missing_file{   s    X%4D-9!!#%*RRHHvHHHHHvHHHHHHHvHHHvHHHHHHHHHHHr   c                 v   t         j                         }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)	u)   로드된 config에 'teams' 키가 있다r-   rW   z%(py1)s in %(py3)sr0   rS   rm   rn   ro   N)
rA   r[   r\   r]   r^   rp   rq   rr   r_   r`   )rb   rG   r0   rc   re   ru   rv   s          r   test_load_config_has_teams_keyz-TestLoadConfig.test_load_config_has_teams_key   si    !!# w&    w&   w      &   &       r   c                 l   t         j                         }t        |t              }|sd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}y)u%   load_config()는 dict를 반환한다5assert %(py4)s
{%(py4)s = %(py0)s(%(py1)s, %(py2)s)
}
isinstancer0   dictrl   rS   py2rT   N)rA   r[   r~   r   rp   rq   r\   rr   r^   r_   r`   )rb   rG   r0   rd   rf   s        r   test_load_config_returns_dictz,TestLoadConfig.test_load_config_returns_dict   s    !!#&$''''''''z'''z''''''&'''&''''''$'''$''''''''''r   c                 8   t         j                         }|d   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
)u'   dev1-team의 name이 '개발1팀'이다r-   r   r    r   rO   rQ   rR   rU   rV   NrZ   ra   s           r   "test_load_config_team_data_correctz1TestLoadConfig.test_load_config_team_data_correct   sk    !!#g{+F3C|C3|CCCC3|CCC3CCC|CCCCCCCr   c                 j   |dz  dz  }|j                  t        d|       t        j                         }|d   }i }||k(  }|slt        j                  d|fd||f      t        j
                  |      t        j
                  |      dz  }dd	|iz  }	t        t        j                  |	            d
x}x}}y
)uC   파일 없을 때 반환되는 기본값의 teams는 빈 dict이다nonexistentr1   r9   r-   rO   rQ   rR   rU   rV   N)r@   rA   r[   r\   r]   r^   r_   r`   )
rb   rB   rC   rs   r0   rc   rd   re   rf   rg   s
             r   (test_load_config_default_has_empty_teamsz7TestLoadConfig.test_load_config_default_has_empty_teams   s    ]*\9D-9!!#g$"$"$$$$"$$$$$$"$$$$$$$r   N)
__name__
__module____qualname____doc__rh   rw   r{   r   r   r    r   r   rM   rM   r   s%    (.I!
(
D
%r   rM   c                   :    e Zd ZdZd Zd Zd Zd Zd Zd Z	d Z
y	)
TestSaveConfigu   save_config() 함수 테스트c                    di i d}t         j                  |       |dz  dz  }|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_config() 호출 후 파일이 생성된다r   rI   r0   r1   Aassert %(py4)s
{%(py4)s = %(py2)s
{%(py2)s = %(py0)s.exists
}()
}rF   rl   r   rT   N)
rA   save_configexistsrp   rq   r\   rr   r^   r_   r`   )rb   rK   rB   r0   rF   rt   rd   rf   s           r   test_save_config_creates_filez,TestSaveConfig.test_save_config_creates_file   s    "RR@ )L8!!#!########{###{###!##########r   c                    dddddgdddg dd	dd
gddi d}t         j                  |       t        j                  |dz  dz  j	                  d            }|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}}|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}}|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}}|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)ue   metadata 필드(total_teams, active_teams, planned_teams, total_members)가 올바르게 계산된다r   u   팀Ar   alicebobr    r"   r$   u   팀Bplannedu   팀Ccharlie)zteam-azteam-bzteam-crI   r0   r1   r6   r7   r.   r'      rO   rQ   rR   rU   rV   Nr(   r2   r)   r%   r*   
rA   r   r=   loads	read_textr\   r]   r^   r_   r`   
rb   rK   rB   r0   savedrc   rd   re   rf   rg   s
             r   !test_save_config_updates_metadataz0TestSaveConfig.test_save_config_updates_metadata   s    #)X7TYJZ[#)Y2N#)X9+V
 
 	 

Hx/,>IISZI[\Z /414/14444/1444/44414444444Z 05A50A55550A5550555A5555555Z 16Q61Q66661Q6661666Q6666666Z 16Q61Q66661Q6661666Q6666666r   c                 P   di i d}t        j                         j                  d      }t        j	                  |       t        j                         j                  d      }t        j                  |dz  dz  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}}|d   }||k  }||k  }|r|st        j                  d||fd|||f      dt        j                         v st        j                  |      rt        j                  |      nd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}x}}y)uA   'updated' 필드가 YYYY-MM-DD HH:MM:SS 형식으로 설정된다r   rI   %Y-%m-%d %H:%M:%Sr0   r1   r6   r7   r,   rW   ry   r   rz   rn   ro   N)<=r   )z%(py0)s <= %(py4)sz%(py4)s <= %(py5)sbeforeafter)rl   rT   ro   assert %(py7)spy7)r   nowstrftimerA   r   r=   r   r   r\   r]   r^   rp   rq   rr   r_   r`   )rb   rK   rB   r0   r   r   r   rc   re   ru   rv   rd   rt   @py_format8s                 r   'test_save_config_sets_updated_timestampz6TestSaveConfig.test_save_config_sets_updated_timestamp   sZ   "RR@(()<= ''(;<

Hx/,>IISZI[\!yE!!!!yE!!!y!!!!!!E!!!E!!!!!!!y)2v)22)U22222v)U222222v222v222)222222U222U2222222r   c                    dddddg dii d}t         j                  |       t        j                  |dz  d	z  j	                  d
            }d}|d   }||v }|slt        j                  d|fd||f      t        j                  |      t        j                  |      dz  }dd|iz  }	t        t        j                  |	            dx}x}}|d   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)u6   teams 데이터가 파일에 올바르게 저장된다r   znew-team	   신규팀r   r   )r    r!   r"   r$   rI   r0   r1   r6   r7   r-   rW   rY   rR   rU   rV   Nr    rO   rQ   r   r   s
             r   test_save_config_persists_teamsz.TestSaveConfig.test_save_config_persists_teams   s    [.T]jlm 
 	 

Hx/,>IISZI[\+U7^+z^++++z^+++z+++^+++++++W~j)&1@[@1[@@@@1[@@@1@@@[@@@@@@@r   c                 "   |dz  dz  dz  }|dz  }|j                          |j                  t        d|       |j                  t        d|       di i d}t        j                  |       |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)uC   CONFIG_FILE의 부모 디렉터리가 없어도 자동 생성된다nesteddeepr1   r-   r9   r:   r   rI   r   rF   r   N)r;   r@   rA   r   r   rp   rq   r\   rr   r^   r_   r`   )	rb   rB   rC   rF   rE   r0   rt   rd   rf   s	            r   #test_save_config_creates_parent_dirz2TestSaveConfig.test_save_config_creates_parent_dir   s    )F2\Aw&	D-=D+y9"RR@ !!#!########{###{###!##########r   c                    di i d}t         j                  |       t        j                  |dz  dz  j	                  d            }|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}}|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}}|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}}|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)u=   teams가 빈 dict일 때 metadata 카운트가 모두 0이다r   rI   r0   r1   r6   r7   r.   r'   r   rO   rQ   rR   rU   rV   Nr(   r)   r*   r   r   s
             r   %test_save_config_empty_teams_metadataz4TestSaveConfig.test_save_config_empty_teams_metadata   s   "RR@ 

Hx/,>IISZI[\Z /414/14444/1444/44414444444Z 05A50A55550A5550555A5555555Z 16Q61Q66661Q6661666Q6666666Z 16Q61Q66661Q6661666Q6666666r   c                    ddddg dii d}t         j                  |       |dz  dz  j                  d	
      }t        j                  |      }t        |t              }|sd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}y)u(   저장된 파일이 유효한 JSON이다r   t   팀r   r   rI   r0   r1   r6   r7   r}   r~   parsedr   r   N)rA   r   r   r=   r   r~   r   rp   rq   r\   rr   r^   r_   r`   )rb   rK   rB   r0   contentr   rd   rf   s           r   test_save_config_valid_jsonz*TestSaveConfig.test_save_config_valid_json   s    "cEXbd3e-ftvw h&5@@'@RG$&$''''''''z'''z''''''&'''&''''''$'''$''''''''''r   N)r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r      s)    ($7&
3A$	7(r   r   c                   j    e Zd ZdZd Zd Zd Zd Zd Zd Z	d Z
d	 Zd
 Zd Zd Zd Zd Zd Zd Zy)TestGenerateTeamIdu#   generate_team_id() 함수 테스트c                 z   t         j                  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*   '개발팀' → 'devteam' 로 변환된다	   개발팀devteamrO   rj   resultrk   rn   ro   N
rA   generate_team_idr\   r]   rp   rq   rr   r^   r_   r`   rb   r   re   rt   ru   rv   s         r   !test_korean_to_english_conversionz4TestGenerateTeamId.test_korean_to_english_conversion  sk    &&{3""v""""v""""""v"""v""""""""""r   c                 z   t         j                  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>   공백은 하이픈으로 변환된다: 'AI 팀' → 'ai-team'u   AI 팀zai-teamrO   rj   r   rk   rn   ro   Nr   r   s         r   test_spaces_to_hyphensz)TestGenerateTeamId.test_spaces_to_hyphens  sk    &&x0""v""""v""""""v"""v""""""""""r   c                 J   t         j                  d      }|j                  } |       }||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t        j                  |      t        j                  |      dz  }dd|iz  }t        t        j                  |            dx}x}}y)	u#   결과는 소문자로 반환된다u   DEV팀rO   )zD%(py0)s == %(py6)s
{%(py6)s = %(py4)s
{%(py4)s = %(py2)s.lower
}()
}r   )rl   r   rT   rV   zassert %(py8)spy8N)rA   r   lowerr\   r]   rp   rq   rr   r^   r_   r`   )rb   r   rd   @py_assert5rt   rg   @py_format9s          r   test_lowercasez!TestGenerateTeamId.test_lowercase  s    &&x0''v''''v''''''v'''v''''''''''''''''''''''r   c                 :   t         j                  d      }|D ]  }g }|j                  } |       }|}|s	d}||k(  }|}|sLddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      dz  }	|j                  |	       |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  }|j                  |       t        j                  |d      i z  }dd|iz  }t        t        j                  |            dx}x}x}x}x}} y)u@   알파벳, 숫자, 하이픈 외의 특수문자는 제거된다u   개발@#$팀!-z;%(py6)s
{%(py6)s = %(py4)s
{%(py4)s = %(py2)s.isalnum
}()
}ch)r   rT   rV   rO   )z%(py8)s == %(py11)s)r   py11z%(py13)spy13r%   zassert %(py16)spy16N)rA   r   isalnumrp   rq   r\   rr   r^   appendr]   _format_boolopr_   r`   )rb   r   r   rt   rd   r   rc   @py_assert10@py_assert9rg   @py_format12@py_format14@py_format15@py_format17s                 r   test_special_chars_removedz-TestGenerateTeamId.test_special_chars_removed  s    &&7 	-B,2::,:<,<,<,29,,,,,,2,,,2,,,:,,,<,,,,<,,,2,,,,,,2,,,2,,,,,,,,,,,,,,,,,	-r   c                 x   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	)
u#   '개발' → 'dev' 로 매핑된다u   개발devrW   ry   r   rz   rn   ro   N
rA   r   r\   r]   r^   rp   rq   rr   r_   r`   rb   r   rc   re   ru   rv   s         r   test_dev_mappingz#TestGenerateTeamId.test_dev_mapping  sj    &&x0uuur   c                 x   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	)
u$   '팀' → 'team' 으로 매핑된다r   teamrW   ry   r   rz   rn   ro   Nr   r   s         r   test_team_mappingz$TestGenerateTeamId.test_team_mapping  sk    &&u-vvvr   c                 x   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	)
u&   '센터' → 'center' 로 매핑된다u   디자인 센터centerrW   ry   r   rz   rn   ro   Nr   r   s         r   test_center_mappingz&TestGenerateTeamId.test_center_mapping$  sl    &&'9:!x6!!!!x6!!!x!!!!!!6!!!6!!!!!!!r   c                 x   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	)
u/   '마케팅' → 'marketing' 으로 매핑된다u   마케팅팀	marketingrW   ry   r   rz   rn   ro   Nr   r   s         r   test_marketing_mappingz)TestGenerateTeamId.test_marketing_mapping)  sk    &&~6${f$$$${f$$${$$$$$$f$$$f$$$$$$$r   c                 x   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	)
u)   '보험' → 'insurance' 로 매핑된다u	   보험팀	insurancerW   ry   r   rz   rn   ro   Nr   r   s         r   test_insurance_mappingz)TestGenerateTeamId.test_insurance_mapping.  sk    &&{3${f$$$${f$$${$$$$$$f$$$f$$$$$$$r   c                 x   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	)
u,   '디자인' → 'design' 으로 매핑된다u   디자인팀designrW   ry   r   rz   rn   ro   Nr   r   s         r   test_design_mappingz&TestGenerateTeamId.test_design_mapping3  sk    &&~6!x6!!!!x6!!!x!!!!!!6!!!6!!!!!!!r   c                 x   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	)
u#   '레드' → 'red' 로 매핑된다u	   레드팀redrW   ry   r   rz   rn   ro   Nr   r   s         r   test_red_mappingz#TestGenerateTeamId.test_red_mapping8  sj    &&{3uuur   c                 x   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	)
u(   '전략' → 'strategy' 로 매핑된다u	   전략팀strategyrW   ry   r   rz   rn   ro   Nr   r   s         r   test_strategy_mappingz(TestGenerateTeamId.test_strategy_mapping=  sk    &&{3#zV####zV###z######V###V#######r   c                 x   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	)
u    기존 하이픈은 유지된다r   r   rW   ry   r   rz   rn   ro   Nr   r   s         r   test_hyphen_preservedz(TestGenerateTeamId.test_hyphen_preservedB  sj    &&{3sf}sfsffr   c                 n   t         j                  d      }t        |t              }|sd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}y)u   반환값은 str 타입이다r   r}   r~   r   strr   N)rA   r   r~   r   rp   rq   r\   rr   r^   r_   r`   )rb   r   rd   rf   s       r   test_returns_stringz&TestGenerateTeamId.test_returns_stringG  s    &&{3&#&&&&&&&&z&&&z&&&&&&&&&&&&&&&&&#&&&#&&&&&&&&&&r   c                 x   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	)
u)   숫자는 유지된다: 'dev1' → 'dev1'r   1rW   ry   r   rz   rn   ro   Nr   r   s         r   test_numeric_suffix_preservedz0TestGenerateTeamId.test_numeric_suffix_preservedL  sj    &&|4sf}sfsffr   N)r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r      sP    -#
#
(-
 
"
%
%
"

$

'
r   r   c                   L    e Zd ZdZd Zd Zd Zd Zd Zd Z	d Z
d	 Zd
 Zd Zy)TestCreateTeamDirectoryu(   create_team_directory() 함수 테스트c                    t         j                  dd       d}||z  }d}||z  }|j                  } |       }|sddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      t        j                  |      dz  }	t        t        j                  |	            dx}x}x}x}x}}y)u    팀 디렉터리가 생성된다	test-team   테스트팀r-   [assert %(py10)s
{%(py10)s = %(py8)s
{%(py8)s = ((%(py0)s / %(py2)s) / %(py5)s).is_dir
}()
}rB   rl   r   ro   r   py10N
rA   create_team_directoryis_dirrp   rq   r\   rr   r^   r_   r`   
rb   rK   rB   rt   rd   @py_assert4@py_assert6@py_assert7r   @py_format11s
             r   test_creates_directoryz.TestCreateTeamDirectory.test_creates_directoryZ  s    "";?":7":[:"[0:088:8::::::::::::::7:::[:::8:::::::::::r   c                    t         j                  dd       |dz  dz  dz  }|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   README.md가 생성된다r  r  r-   	README.mdr   readmer   N
rA   r	  r   rp   rq   r\   rr   r^   r_   r`   )rb   rK   rB   r  rt   rd   rf   s          r   test_creates_readmez+TestCreateTeamDirectory.test_creates_readme_  s}    "";?G#k1K?}}}vv}r   c                    t         j                  dd       |dz  dz  dz  }|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)u'   README.md에 팀 이름이 포함된다r  r  r-   r  r6   r7   rW   ry   r   rz   rn   ro   N)rA   r	  r   r\   r]   r^   rp   rq   rr   r_   r`   )	rb   rK   rB   r  r   rc   re   ru   rv   s	            r   test_readme_contains_team_namez6TestCreateTeamDirectory.test_readme_contains_team_namee  s    "";?G#k1K?""G"4(~((((~(((~((((((((((((((((r   c                    t         j                  dd       |dz  dz  }d}||z  }|j                  } |       }|sddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      dz  }t        t        j                  |            dx}x}x}}d	}||z  }|j                  } |       }|sddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      dz  }t        t        j                  |            dx}x}x}}d
}||z  }|j                  } |       }|sddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      dz  }t        t        j                  |            dx}x}x}}y)u7   src/, tests/, docs/ 하위 디렉터리가 생성된다r  r  r-   srczMassert %(py7)s
{%(py7)s = %(py5)s
{%(py5)s = (%(py0)s / %(py2)s).is_dir
}()
}team_dir)rl   r   ro   r   Ntestsdocsr  )	rb   rK   rB   r  rt   rd   r  r  r   s	            r   test_creates_subdirsz,TestCreateTeamDirectory.test_creates_subdirsl  s   "";?g%3 *5 * ((*(**************5***(**********",7","**,*,,,,,,,,,,,,,,7,,,*,,,,,,,,,,!+6!+!))+)++++++++++++++6+++)++++++++++r   c           
      t   t         j                  dd       d}||z  }d}||z  }d}||z  }d}	||	z  }
|
j                  } |       }|sddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      t        j                  |	      t        j                  |      t        j                  |      dz  }t        t        j                  |            d	x}x}x}x}x}x}x}	x}
x}}y	)
u   src/.gitkeep이 생성된다r  r  r-   r  .gitkeepvassert %(py16)s
{%(py16)s = %(py14)s
{%(py14)s = ((((%(py0)s / %(py2)s) / %(py5)s) / %(py8)s) / %(py11)s).exists
}()
}rB   rl   r   ro   r   r   py14r   Nr  rb   rK   rB   rt   rd   r  r  r  r   r   @py_assert12@py_assert13@py_assert15r   s                 r   test_creates_gitkeep_in_srcz3TestCreateTeamDirectory.test_creates_gitkeep_in_srct  s    "";?"O7"O[O"[0O5O058O:O8:EOEMMOMOOOOOOOOOOOOOO7OOO[OOO5OOO:OOOMOOOOOOOOOOOOr   c           
      t   t         j                  dd       d}||z  }d}||z  }d}||z  }d}	||	z  }
|
j                  } |       }|sddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      t        j                  |	      t        j                  |      t        j                  |      dz  }t        t        j                  |            d	x}x}x}x}x}x}x}	x}
x}}y	)
u   tests/.gitkeep이 생성된다r  r  r-   r  r  r   rB   r!  Nr  r#  s                 r   test_creates_gitkeep_in_testsz5TestCreateTeamDirectory.test_creates_gitkeep_in_testsy  s    "";?"Q7"Q[Q"[0Q7Q07:QZQ:ZGQGOOQOQQQQQQQQQQQQQQ7QQQ[QQQ7QQQZQQQOQQQQQQQQQQQQr   c                    |dz  dz  }|j                  d       |dz  }d}|j                  |d       t        j                  dd	       |j                  }d} ||      }||k(  }	|	st        j                  d
|	fd||f      dt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      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}x}x}}	y)u7   README.md가 이미 존재하면 덮어쓰지 않는다r-   r  T)parentsr  u   # 기존 README 내용r6   r7   r  rO   )zX%(py6)s
{%(py6)s = %(py2)s
{%(py2)s = %(py0)s.read_text
}(encoding=%(py4)s)
} == %(py8)sr  original_content)rl   r   rT   rV   r   assert %(py10)sr  N)r;   r<   rA   r	  r   r\   r]   rp   rq   rr   r^   r_   r`   )rb   rK   rB   r  r  r,  rt   rd   r   r  r   r  s               r   test_readme_not_overwrittenz3TestCreateTeamDirectory.test_readme_not_overwritten~  s   g%3t$K'3*W="";?EE1E15EEEEE15EEEEEEEvEEEvEEEEEEEEE1EEEEEE5EEEE5EEEEEEEEEr   c                 p   t         j                  dd      }t        |t              }|sd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}y)	u   반환값이 Path 객체이다r  r  r}   r~   r   r   r   N)rA   r	  r~   r   rp   rq   r\   rr   r^   r_   r`   )rb   rK   rB   r   rd   rf   s         r   test_returns_pathz)TestCreateTeamDirectory.test_returns_path  s    ++KH&$''''''''z'''z''''''&'''&''''''$'''$''''''''''r   c                 J   t         j                  dd      }d}||z  }d}||z  }||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t        j                  |      t        j                  |      dz  }	d	d
|	iz  }
t        t        j                  |
            dx}x}x}x}}y)u9   반환된 Path가 실제 팀 디렉터리를 가리킨다r  r  r-   rO   )z*%(py0)s == ((%(py2)s / %(py4)s) / %(py7)s)r   rB   rl   r   rT   r   r-  r  N)
rA   r	  r\   r]   rp   rq   rr   r^   r_   r`   )rb   rK   rB   r   rd   r   r  @py_assert8rt   r   r  s              r   test_returns_correct_pathz1TestCreateTeamDirectory.test_returns_correct_path  s    ++KH$+9G+9k9+k99v99999v9999999v999v999999999999G999k99999999r   c                 $   t         j                  dd       t         j                  dd       d}||z  }d}||z  }|j                  } |       }|sddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      t        j                  |      dz  }	t        t        j                  |	            dx}x}x}x}x}}y)u?   두 번 호출해도 오류 없이 동작한다 (exist_ok=True)r  r  r-   r  rB   r  Nr  r  s
             r   test_idempotent_callz,TestCreateTeamDirectory.test_idempotent_call  s    "";?"";?":7":[:"[0:088:8::::::::::::::7:::[:::8:::::::::::r   N)r   r   r   r   r  r  r  r  r'  r)  r.  r0  r4  r6  r   r   r   r  r  W  s:    2;
),P
R

F(
:
;r   r  c                   d    e Zd ZdZd Zd Zd Zd Zd Zd Z	d Z
d	 Zd
 Zd Zd Zd Zd Zd Zy)TestAddTeamu   add_team() 함수 테스트c                     t         j                  dddd      }t        j                  |dz  dz  j	                  d	            }|d
   }|d   }||v }|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}}d}||z  }
|
|z  }|j                  } |       }|sddt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      d
t        j                         v st        j                  |      rt        j                  |      nd
t        j                  |      t        j                  |      dz  }t        t        j                  |            dx}x}
x}x}}y)uK   새 팀을 추가하면 config에 저장되고 디렉터리가 생성된다r   r   zeusr   )r    	team_typer#   r"   r0   r1   r6   r7   team_idr-   rW   )z%(py0)s in %(py3)srk   rn   ro   NzYassert %(py9)s
{%(py9)s = %(py7)s
{%(py7)s = ((%(py0)s / %(py2)s) / %(py4)s).is_dir
}()
}rB   )rl   r   rT   r   py9)rA   r	   r=   r   r   r\   r]   rp   rq   rr   r^   r_   r`   r
  )rb   rK   rB   r   r   r<  re   rt   ru   rv   rd   r   r  r3  @py_format10s                  r   test_add_new_teamzTestAddTeam.test_add_new_team  sR   K>PV_hi 

Hx/,>IISZI[\#.(w.((((w.((((((w(((w(((.((((((( #67"6"W,6,4464666666666666667666666W666W666466666666666r   c                    t         j                         }t        |d   j                               d   }t	        j
                  t              5 }t         j                  dd       t         j                  dd       ddd       j                  }|j                  }d}||k(  }|st        j                  d|fd	||f      d
t        j                         v st        j                  |      rt        j                  |      nd
t        j                  |      t        j                  |      t        j                  |      dz  }	dd|	iz  }
t!        t        j"                  |
            dx}x}x}}y# 1 sw Y   xY w)uE   이미 존재하는 team_id로 추가 시 sys.exit(1)이 호출된다r-   r   r   r   r    r;  Nr%   rO   zG%(py4)s
{%(py4)s = %(py2)s
{%(py2)s = %(py0)s.value
}.code
} == %(py7)sexc_infor2  assert %(py9)sr=  )rA   r[   listkeyspytestraises
SystemExitr	   valuecoder\   r]   rp   rq   rr   r^   r_   r`   )rb   rG   r0   existing_idrC  rt   rd   r  r   r   r>  s              r   test_duplicate_team_exitsz%TestAddTeam.test_duplicate_team_exits  s     !!#6'?//1215
 ]]:& 	G(MM|~MFMM|~MF	G ~~'~""'a'"a''''"a''''''x'''x'''~'''"'''a'''''''	G 	Gs   /E//E8c                    t         j                  ddd       t        j                  t              5 }t         j                  ddd       ddd       j
                  }|j                  }d}||k(  }|st        j                  d|fd||f      d	t        j                         v st        j                  |      rt        j                  |      nd	t        j                  |      t        j                  |      t        j                  |      d
z  }dd|iz  }t        t        j                  |            dx}x}x}}y# 1 sw Y   xY w)uI   첫 번째 add 이후 동일 이름으로 다시 추가하면 sys.exit(1)u   AI팀r   r   r    r;  r"   Nr%   rO   rB  rC  r2  rD  r=  )rA   r	   rG  rH  rI  rJ  rK  r\   r]   rp   rq   rr   r^   r_   r`   )	rb   rK   rC  rt   rd   r  r   r   r>  s	            r   test_duplicate_team_id_detectedz+TestAddTeam.test_duplicate_team_id_detected  s    7nYO]]:& 	T(MMw.MS	T~~'~""'a'"a''''"a''''''x'''x'''~'''"'''a'''''''	T 	Ts   D>>Ec                    t         j                  d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}}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}}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)u=   반환된 dict에 team_id, team_info, directory 키가 있다r  r   rA  r<  rW   ry   r   rz   rn   ro   N	team_info	directory)
rA   r	   r\   r]   r^   rp   rq   rr   r_   r`   )rb   rK   r   rc   re   ru   rv   s          r   test_team_info_structurez$TestAddTeam.test_team_info_structure  s   NnM"yF""""yF"""y""""""F"""F"""""""${f$$$${f$$${$$$$$$f$$$f$$$$$$$${f$$$${f$$${$$$$$$f$$$f$$$$$$$r   c                 f   t         j                  ddd      }|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}}|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}}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}}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}}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}}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)uD   team_info에 name, type, status, lead, members, created_at이 있다r  r   r:  r    r;  r#   rR  r    rO   rQ   rR   rU   rV   Nr!   r"   rW   ry   inforz   rn   ro   r#   r$   
created_at)
rA   r	   r\   r]   r^   r_   r`   rp   rq   rr   )rb   rK   r   rW  rc   rd   re   rf   rg   ru   rv   s              r   'test_team_info_contains_required_fieldsz3TestAddTeam.test_team_info_contains_required_fields  s    NnSYZk"F|-~-|~----|~---|---~-------F|-~-|~----|~---|---~-------x4x4x44v~vv yD    yD   y      D   D       #|t####|t###|######t###t#######r   c                 8   t         j                  dd      }|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)u1   status 미지정 시 기본값은 'planned'이다u   기본상태팀r   rA  rR  r"   r   rO   rQ   rR   rU   rV   NrA   r	   r\   r]   r^   r_   r`   rb   rK   r   rc   rd   re   rf   rg   s           r   test_default_status_plannedz'TestAddTeam.test_default_status_planned  sl    $5Pk"8,9	9,	9999,	999,999	9999999r   c                 8   t         j                  dd      }|d   d   }g }||k(  }|slt        j                  d|fd||f      t        j                  |      t        j                  |      dz  }d	d
|iz  }t        t        j                  |            dx}x}}y)u6   members 미지정 시 기본값은 빈 리스트이다u   빈멤버팀r   rA  rR  r$   rO   rQ   rR   rU   rV   Nr[  r\  s           r   test_members_default_emptyz&TestAddTeam.test_members_default_empty  sk    NnMk"9-33-3333-333-3333333333r   c                 :   t         j                  ddd      }|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)u.   lead가 team_info에 올바르게 저장된다u	   리더팀r   poseidonrV  rR  r#   rO   rQ   rR   rU   rV   Nr[  r\  s           r   test_lead_stored_correctlyz&TestAddTeam.test_lead_stored_correctly  sn    K>PZ[k"6*8j8*j8888*j888*888j8888888r   c                 B   t         j                  ddddg      }|d   d   }ddg}||k(  }|slt        j                  d|fd	||f      t        j                  |      t        j                  |      d
z  }dd|iz  }t        t        j                  |            dx}x}}y)u.   전달된 members가 team_info에 저장된다	   멤버팀r   r   r   )r    r;  r$   rR  r$   rO   rQ   rR   rU   rV   Nr[  r\  s           r   test_members_stored_correctlyz)TestAddTeam.test_members_stored_correctly  s|    K>T[]bScdk"9-A'51AA-1AAAAA-1AAAA-AAA1AAAAAAAAr   c                 :   t         j                  ddd      }|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)u,   status='active'가 올바르게 저장된다u	   활성팀r   r   rO  rR  r"   rO   rQ   rR   rU   rV   Nr[  r\  s           r   test_active_status_storedz%TestAddTeam.test_active_status_stored  sn    K>RZ[k"8,88,8888,888,8888888888r   c                 8   t         j                  dd      }|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)u3   team_type이 team_info에 올바르게 저장된다u   횡단조직팀   횡단조직rA  rR  r!   rO   rQ   rR   rU   rV   Nr[  r\  s           r   test_team_type_storedz!TestAddTeam.test_team_type_stored  sl    $5Pk"6*<n<*n<<<<*n<<<*<<<n<<<<<<<r   c                 n    t         j                  dd      }|d   d   }t        j                  |d       y)u.   created_at이 YYYY-MM-DD HH:MM:SS 형식이다u   타임스탬프팀r   rA  rR  rX  r   N)rA   r	   r   strptime)rb   rK   r   rX  s       r   test_created_at_formatz"TestAddTeam.test_created_at_format  s5    $8NSK(6
*&9:r   c                    t         j                  dd      }t        |d         }|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)	u9   add_team() 후 팀 디렉터리가 실제로 생성된다u	   디렉팀r   rA  rS  zAassert %(py4)s
{%(py4)s = %(py2)s
{%(py2)s = %(py0)s.is_dir
}()
}r  r   N)rA   r	   r   r
  rp   rq   r\   rr   r^   r_   r`   )rb   rK   rB   r   r  rt   rd   rf   s           r   test_directory_createdz"TestAddTeam.test_directory_created   s}    K>J{+,         x   x             r   c                    t         j                  dd      }t        j                  |dz  dz  j	                  d            }|d   }|d	   }||v }|slt        j                  d
|fd||f      t        j                  |      t        j                  |      dz  }dd|iz  }	t        t        j                  |	            dx}x}}y)u:   add_team() 후 config 파일에 팀 정보가 저장된다u	   저장팀r   rA  r0   r1   r6   r7   r<  r-   rW   rY   rR   rU   rV   N)
rA   r	   r=   r   r   r\   r]   r^   r_   r`   )
rb   rK   rB   r   r   rc   rd   re   rf   rg   s
             r   test_config_saved_to_filez%TestAddTeam.test_config_saved_to_file  s    K>J

Hx/,>IISZI[\i 2E'N2 N2222 N222 222N2222222r   N)r   r   r   r   r?  rM  rP  rT  rY  r]  r_  rb  re  rg  rj  rm  ro  rq  r   r   r   r8  r8    sL    %
7("(%	$:
4
9
B
9
=
;!3r   r8  c                   L    e Zd ZdZd Zd Zd Zd Zd Zd Z	d Z
d	 Zd
 Zd Zy)TestListTeamsu   list_teams() 함수 테스트c                    t         j                          |j                         }d}|j                  }||v }|st	        j
                  d|fd||f      t	        j                  |      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}x}}y)	u,   팀이 있을 때 팀 정보를 출력한다r   rW   z+%(py1)s in %(py5)s
{%(py5)s = %(py3)s.out
}capturedrS   rm   ro   r   r   NrA   
list_teams
readouterroutr\   r]   r^   rp   rq   rr   r_   r`   	rb   rG   capsysrv  rc   r  re   rv   r   s	            r   test_list_teams_with_dataz'TestListTeams.test_list_teams_with_data  s    $$&*hll*{l****{l***{******h***h***l*******r   c                    t         j                          |j                         }d}|j                  }||v }|st	        j
                  d|fd||f      t	        j                  |      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}x}}y)	uB   팀이 없을 때 '등록된 팀이 없습니다.'를 출력한다   등록된 팀이 없습니다.rW   ru  rv  rw  r   r   Nrx  )	rb   rK   r}  rv  rc   r  re   rv   r   s	            r   test_list_teams_emptyz#TestListTeams.test_list_teams_empty  s    $$&/?8<<?/<????/<???/??????8???8???<???????r   c                    t         j                          |j                         }d}|j                  }||v }|st	        j
                  d|fd||f      t	        j                  |      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}x}}y)	u2   팀 이름('개발1팀')이 출력에 포함된다r   rW   ru  rv  rw  r   r   Nrx  r|  s	            r   test_list_teams_shows_team_namez-TestListTeams.test_list_teams_shows_team_name!  s    $$&+x||+||++++||+++|++++++x+++x+++|+++++++r   c                    t         j                          |j                         }d}|j                  }||v }|st	        j
                  d|fd||f      t	        j                  |      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}x}}y)	u.   팀 리더('hermes')가 출력에 포함된다r   rW   ru  rv  rw  r   r   Nrx  r|  s	            r   test_list_teams_shows_leadz(TestListTeams.test_list_teams_shows_lead'  s    $$&'8<<'x<''''x<'''x''''''8'''8'''<'''''''r   c                    t         j                          |j                         }d}|j                  }||v }|st	        j
                  d|fd||f      t	        j                  |      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}x}}y)	u*   팀원 수(4명)가 출력에 포함된다4rW   ru  rv  rw  r   r   Nrx  r|  s	            r   "test_list_teams_shows_member_countz0TestListTeams.test_list_teams_shows_member_count-  s    $$&"hll"sl""""sl"""s""""""h"""h"""l"""""""r   c                    t         j                          |j                         }d}|j                  }||v }|st	        j
                  d|fd||f      t	        j                  |      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}x}}y)	u%   총 팀 수가 출력에 포함된다u   총rW   ru  rv  rw  r   r   Nrx  r|  s	            r   test_list_teams_shows_totalz)TestListTeams.test_list_teams_shows_total3  s    $$&$$u$$$$u$$$u$$$$$$$$$$$$$$$$$$$r   c                    t         j                          |j                         }d}|j                  }||v }|st	        j
                  d|fd||f      t	        j                  |      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}x}}y)	u4   팀 유형('수직조직')이 출력에 포함된다r   rW   ru  rv  rw  r   r   Nrx  r|  s	            r   test_list_teams_shows_typez(TestListTeams.test_list_teams_shows_type9  s    $$&--~----~---~-------------------r   c                    t         j                          |j                         }d}d}||z  }|j                  }||v }|st	        j
                  d|fd||f      t	        j                  |      t	        j                  |      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}x}x}x}}y	)
u(   구분선('=')이 출력에 포함된다=
   rW   )z7(%(py1)s * %(py3)s) in %(py8)s
{%(py8)s = %(py6)s.out
}rv  )rS   rm   rV   r   r-  r  Nrx  )rb   rG   r}  rv  rc   re   r  r  r   r   r  s              r   test_list_teams_shows_separatorz-TestListTeams.test_list_teams_shows_separator?  s    $$&'R'sRx'8<<'x<''''x<'''s'''R''''''8'''8'''<''''''''r   c                    t         j                  dd       t         j                  dd       t         j                          |j                         }d}|j                  }||v }|st        j                  d|fd||f      t        j                  |      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}x}}d}|j                  }||v }|st        j                  d|fd||f      t        j                  |      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}x}}y)u,   여러 팀이 있을 때 모두 출력된다u	   팀알파r   rA  u	   팀베타ri  rW   ru  rv  rw  r   r   N)rA   r	   ry  rz  r{  r\   r]   r^   rp   rq   rr   r_   r`   )
rb   rK   rB   r}  rv  rc   r  re   rv   r   s
             r   test_list_teams_multiple_teamsz,TestListTeams.test_list_teams_multiple_teamsE  s   ;.A;.A$$&*hll*{l****{l***{******h***h***l********hll*{l****{l***{******h***h***l*******r   c                 v   t         j                         }d}||u }|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_teams()는 None을 반환한다N)is)z%(py0)s is %(py3)sr   rk   rn   ro   )
rA   ry  r\   r]   rp   rq   rr   r^   r_   r`   )rb   rG   r   re   rt   ru   rv   s          r   test_list_teams_returns_nonez*TestListTeams.test_list_teams_returns_noneO  sf    "v~vvvr   N)r   r   r   r   r~  r  r  r  r  r  r  r  r  r  r   r   r   rs  rs    s8    '+@,(#%.(+r   rs  c                   X    e Zd ZdZd Zd Zd Zd Zd Zd Z	d Z
d	 Zd
 Zd Zd Zd Zy)TestCLIMainu   main() CLI 함수 테스트c                    |j                  t        dddg       t        j                          |j	                         }d}|j
                  }||v }|st        j                  d|fd||f      t        j                  |      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}x}}y)u.   --list 플래그로 팀 목록이 출력된다argvr   --listr   rW   ru  rv  rw  r   r   Nr@   sysrA   mainrz  r{  r\   r]   r^   rp   rq   rr   r_   r`   )
rb   rG   rC   r}  rv  rc   r  re   rv   r   s
             r   test_list_flagzTestCLIMain.test_list_flag]  s    C-)BC		$$&*hll*{l****{l***{******h***h***l*******r   c                 ^    |j                  t        dddg       t        j                          y)uD   --list 플래그 실행 후 반환 (add_team이 호출되지 않음)r  r   r  N)r@   r  rA   r  )rb   rG   rC   r}  s       r   test_list_flag_shortz TestCLIMain.test_list_flag_shortd  s"    C-)BC		r   c                    |j                  t        dg d       t        j                          t	        j
                  |dz  dz  j                  d            }|d   }t        |      }d}||k(  }	|	st        j                  d	|	fd
||f      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}	}y)u4   --name과 --type이 제공되면 팀이 추가된다r  )r   --nameu   CLI테스트팀--typer   r0   r1   r6   r7   r-   r%   rO   )z0%(py4)s
{%(py4)s = %(py0)s(%(py2)s)
} == %(py7)slenr2  rD  r=  N)r@   r  rA   r  r=   r   r   r  r\   r]   rp   rq   rr   r^   r_   r`   )rb   rK   rB   rC   r}  r   rt   rd   r  r   r   r>  s               r   test_add_team_via_cliz!TestCLIMain.test_add_team_via_clij  s    R	
 			

Hx/,>IISZI[\>'s>"'a'"a''''"a''''''s'''s'''>'''"'''a'''''''r   c                    |j                  t        dg d       t        j                          |j	                         }g }d}|j
                  }||v }|}	|sd}
|j
                  }|
|v }|}	|	st        j                  d|fd||f      t        j                  |      dt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      dz  }d	d
|iz  }|j                  |       |st        j                  dfd
f      t        j                  |
      dt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      dz  }dd|iz  }|j                  |       t        j                  |d      i z  }dd|iz  }t        t        j                  |            dx}	x}x}x}x}x}
x}}y)u6   팀 추가 성공 시 성공 메시지가 출력된다r  )r   r  u   출력테스트팀r  r   --leadr:  u   완료u   ✅rW   )z+%(py3)s in %(py7)s
{%(py7)s = %(py5)s.out
}rv  )rm   ro   r   z%(py9)sr=  )z/%(py12)s in %(py16)s
{%(py16)s = %(py14)s.out
})py12r"  r   z%(py18)spy18r%   zassert %(py21)spy21N)r@   r  rA   r  rz  r{  r\   r]   r^   rp   rq   rr   r   r   r_   r`   )rb   rK   rC   r}  rv  rt   re   r  r  rc   @py_assert11r&  r%  r   r>  r   @py_format19@py_format20@py_format22s                      r   test_add_team_cli_outputz$TestCLIMain.test_add_team_cli_outputu  s   g	
 			$$&@x@8<<@x<'@5@HLL@5L+@@@@@x<@@@x@@@@@@8@@@8@@@<@@@@@@@5L@@@5@@@@@@H@@@H@@@L@@@@@@@@@@@@@@r   c                    |j                  t        dg d       t        j                  t              5 }t
        j                          ddd       j                  }|j                  }d}||k(  }|st        j                  d|fd||f      dt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      dz  }d	d
|iz  }	t        t        j                   |	            dx}x}x}}y# 1 sw Y   xY w)u/   --name이 없으면 sys.exit(1)이 호출된다r  )r   r  r   Nr%   rO   rB  rC  r2  rD  r=  r@   r  rG  rH  rI  rA   r  rJ  rK  r\   r]   rp   rq   rr   r^   r_   r`   
rb   rK   rC   rC  rt   rd   r  r   r   r>  s
             r    test_missing_required_name_exitsz,TestCLIMain.test_missing_required_name_exits  s    C)RS]]:& 	(IIK	~~'~""'a'"a''''"a''''''x'''x'''~'''"'''a'''''''	 	   D;;Ec                    |j                  t        dg d       t        j                  t              5 }t
        j                          ddd       j                  }|j                  }d}||k(  }|st        j                  d|fd||f      dt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      dz  }d	d
|iz  }	t        t        j                   |	            dx}x}x}}y# 1 sw Y   xY w)u/   --type이 없으면 sys.exit(1)이 호출된다r  )r   r  u   타입없는팀Nr%   rO   rB  rC  r2  rD  r=  r  r  s
             r    test_missing_required_type_exitsz,TestCLIMain.test_missing_required_type_exits  s    C)UV]]:& 	(IIK	~~'~""'a'"a''''"a''''''x'''x'''~'''"'''a'''''''	 	r  c                    |j                  t        ddg       t        j                  t              5 }t
        j                          ddd       j                  }|j                  }d}||k(  }|st        j                  d|fd||f      dt        j                         v st        j                  |      rt        j                  |      ndt        j                  |      t        j                  |      t        j                  |      dz  }d	d
|iz  }	t        t        j                   |	            dx}x}x}}y# 1 sw Y   xY w)u6   인수 없이 실행하면 sys.exit(1)이 호출된다r  r   Nr%   rO   rB  rC  r2  rD  r=  r  r  s
             r   test_no_args_exitszTestCLIMain.test_no_args_exits  s    C-9]]:& 	(IIK	~~'~""'a'"a''''"a''''''x'''x'''~'''"'''a'''''''	 	s   D::Ec                    |j                  t        dg d       t        j                          t	        j
                  |dz  dz  j                  d            }t        |d   j                               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}}|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)u5   --lead, --status 인수가 팀 정보에 반영된다r  )	r   r  u   리더상태팀r  r   r  apollo--statusr   r0   r1   r6   r7   r-   r   r#   r  rO   rQ   rR   rU   rV   Nr"   r   r@   r  rA   r  r=   r   r   rE  valuesr\   r]   r^   r_   r`   rb   rK   rB   rC   r   r   rc   rd   re   rf   rg   s              r   test_cli_with_lead_and_statusz)TestCLIMain.test_cli_with_lead_and_status  s   		
 			

Hx/,>IISZI[\E'N))+,Q/F|'x'|x''''|x'''|'''x'''''''H~))~))))~)))~))))))))))r   c                    |j                  t        dg d       t        j                          t	        j
                  |dz  dz  j                  d            }t        |d   j                               d   }d	}|d
   }||v }|slt        j                  d|fd||f      t        j                  |      t        j                  |      dz  }	dd|	iz  }
t        t        j                  |
            dx}x}}d}|d
   }||v }|slt        j                  d|fd||f      t        j                  |      t        j                  |      dz  }	dd|	iz  }
t        t        j                  |
            dx}x}}y)u.   --members 인수가 팀 멤버에 반영된다r  )r   r  rd  r  r   z	--membersr   r   r0   r1   r6   r7   r-   r   r   r$   rW   rY   rR   rU   rV   Nr   r  r  s              r   test_cli_with_membersz!TestCLIMain.test_cli_with_members  s   	
 			

Hx/,>IISZI[\E'N))+,Q/)$y/)w/))))w/)))w)))/)))))))'Y'u''''u'''u''''''''''r   c                     |j                  t        dg d       t        j                  t              5  t
        j                          ddd       y# 1 sw Y   yxY w)ud   --type에 유효하지 않은 값을 전달하면 sys.exit이 호출된다 (argparse choices 검증)r  )r   r  u   잘못된유형팀r  u   잘못된유형Nr@   r  rG  rH  rI  rA   r  rb   rK   rC   s      r   test_cli_invalid_type_exitsz'TestCLIMain.test_cli_invalid_type_exits  sD    X	
 ]]:& 	IIK	 	 	   AAc                     |j                  t        dg d       t        j                  t              5  t
        j                          ddd       y# 1 sw Y   yxY w)uf   --status에 유효하지 않은 값을 전달하면 sys.exit이 호출된다 (argparse choices 검증)r  )r   r  u   잘못된상태팀r  r   r  invalidNr  r  s      r   test_cli_invalid_status_exitsz)TestCLIMain.test_cli_invalid_status_exits  sD    l	
 ]]:& 	IIK	 	 	r  c                    |j                  t        dddg       t        j                          |j	                         }d}|j
                  }||v }|st        j                  d|fd||f      t        j                  |      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}x}}y)uL   팀이 없을 때 --list는 '등록된 팀이 없습니다.'를 출력한다r  r   r  r  rW   ru  rv  rw  r   r   Nr  )
rb   rK   rC   r}  rv  rc   r  re   rv   r   s
             r   test_cli_list_empty_configz&TestCLIMain.test_cli_list_empty_config  s    C-)BC		$$&/?8<<?/<????/<???/??????8???8???<???????r   N)r   r   r   r   r  r  r  r  r  r  r  r  r  r  r  r  r   r   r   r  r  Z  sC    %+	(A(((*&($@r   r  )!r   builtinsrp   _pytest.assertion.rewrite	assertionrewriter\   importlib.utilr
   r=   osr  r   pathlibr   rG  environget
_WORKSPACEr   r   rA   r?   fixturerG   rK   rM   r   r   r  r8  rs  r  r   r   r   <module>r     s2  "     	 
    "**..!13HIJ
I%5 ~ $ "<
 	*  $  0&% &%\X( X(@O OnB; B;Ti3 i3b@ @Pv@ v@r   