
    i                       d Z ddlmZ ddlZddlZddlZddlZddlZddlZddl	Z	ddl
Z
ddlmZ dZdZdZdZg dZ ej$                  d	      Zdd
Z	 	 	 	 	 	 ddZddZddZedk(  r e	j2                   e              yy)um  
auto_e2e_gate.py — task-2385 Phase γ 머지 전 자동 E2E 회귀 차단 게이트

InsuRo 변경 감지 시 6 시나리오 Playwright 자동 실행. 회장 = 베타테스터 패턴 종료.

Exit codes:
  0 = PASS (또는 InsuRo 무관 → skip)
  1 = FAIL (시나리오 1건 이상 실패)
  2 = INFRA_FAIL (timeout, playwright 미설치 등 인프라 문제)
    )annotationsN)Path      )zserver/zsrc/z
extension/zpublic/)z01-main-load.spec.tsz02-composite-design.spec.tsz03-info-keyword.spec.tsz04-dashboard.spec.tsz05-pwa-sw.spec.tsz06-console-errors.spec.tsauto_e2e_gatec                R   | dz  j                         sg S 	 t        j                  ddt        |       dddgddd	      }|j                  d
k7  r<t
        j                  d|j                  |j                  j                                dgS |j                  j                         D cg c]  }|j                         s| }}|D cg c]  t        fdt        D              s }}|S c c}w c c}w # t        j                  $ r t
        j                  d       dgcY S w xY w)u]   git diff --name-only main..HEAD에서 InsuRo 핵심 디렉토리 매칭 파일 목록 반환.z.gitgitz-Cdiffz--name-onlyz
main..HEADT   )capture_outputtexttimeoutr   uO   git diff main..HEAD 실패 (rc=%s): %s — 보수적으로 변경 있음 처리	__force__c              3  @   K   | ]  }j                  |        y w)N)
startswith).0pfs     scripts/auto_e2e_gate.py	<genexpr>z(detect_insuro_changes.<locals>.<genexpr>7   s     *Sq1<<?*Ss   u9   git diff timeout — 보수적으로 변경 있음 처리)exists
subprocessrunstr
returncodeloggerwarningstderrstripstdout
splitlinesanyWATCH_PATTERNSTimeoutExpired)project_pathresultlinefilesr   matcheds       ` r   detect_insuro_changesr*   (   s#   6!))+	D#l+V]LQdB
 !NNlntnn  BH  BO  BO  BU  BU  BW  X= "(--":":"<M$

MM#Ts*SN*S'S1TT NT$$ RS}sB   A2C8 C8 'C.=C.C8 C3&C3*C8 .
C8 8+D&%D&c           	     "   t        j                  d      t        dddfS g }t        D ]A  }||z  }|j	                         st        dd| dfc S |j                  t        |             C |j                  dd       |d	z  j                  d
       |dz  }t        j                  j                         }	t        |      |	d<   ||	d<   t        |      |	d<   dddg|dd| d}
t        j                  ddj                  |
             t        j                         }	 t!        j"                  |
| |	dd|      }t        j                         |z
  }|j*                  j-                         xs d}|j	                         r	 |j/                  d      }	 t3        j4                  |      }t9        |t:              r|nd|dd i}g }g }|j=                  d g       D ]  }t9        |t:              s|j=                  d!g       D ]  }t9        |t:              s|j=                  d"d#      }|j                  |j=                  d$d%      |j=                  d&d%      |d'       |r^|j                  |j=                  d$d%      |j=                  d&d%      t?        |      d(         |j@                  d)k(  r|stB        d*|t)        |d      d+fS tD        d,||t)        |d      |j@                  |jF                  r|jF                  d-d d/fS d.d/fS # t         j$                  $ rG t        j                         |z
  }t        j'                  d|       t        dd|t)        |d      dfcY S w xY w# t0        $ r Y w xY w# t2        j6                  $ r d}Y w xY w)0u3   Playwright 실행. (exit_code, result_dict) 반환.npxN
infra_failnpx_missing)statusreasonzscenario_missing:Tparentsexist_okscreenshots)r3   zplaywright-report.jsonAUTO_E2E_GATE_OUTPUT_DIRAUTO_E2E_GATE_TASK_IDPLAYWRIGHT_JSON_OUTPUT_NAME
playwrighttestz--reporter=jsonz	--output=z/test-resultsu   Playwright 실행: %s )cwdenvr   r   r   u   Playwright timeout %ds 초과r   r   )r/   r0   timeout_secduration_secz{}utf-8encodingrawi  suitesspecsokFtitle?file)rF   rH   rE   )rF   rH   errorr   pass)r/   	scenariosr>   faili0 )r/   failuresrK   r>   playwright_exitstderr_tail)$shutilwhichEXIT_INFRA_FAILSCENARIO_FILESr   appendr   mkdirosenvironcopyr   infojointime	monotonicr   r   r$   rI   roundr    r   	read_textOSErrorjsonloadsJSONDecodeError
isinstancedictget_extract_errorr   	EXIT_PASS	EXIT_FAILr   )r%   scenarios_dir
output_dirtask_idr=   
spec_filesnamepathreport_pathr<   cmdstartprocdurationraw_jsonparsedreportscenarios_summaryrN   suitespecrE   s                         r   run_playwrightr{   >   s    ||E"<= QQQ J %t#{{}"|IZ[_Z`Ga$bbb#d)$	% TD1-&&&577K
**//
C&)*oC"##*C ),[)9C%& 	|V	 	 J<}-	C KK'#7NNE
~~\sdK
 ~~%'H {{  "*dH	",,g,>HH% (56E8ET?;SFHHb) %&IIgr* 	DdD)$&B$$'3/-& 
 !XXgs3 HHVS1+D1! 	& !H*!(A.
 
 	
  *!(A.#26++4;;uv.
 
 	
 DF
 
 	
i $$ 
>>#e+4kB"&!(A.	!
 
 	

   		  s7   "L M% M5 AM"!M"%	M21M25NNc                4   | j                  dg       D ]  }|j                  dg       D ]l  }|j                  d      }t        |t              r)|j                  d      xs |j                  d      xs d}nt        |t              r|}nd}|se|d d c c S   y)NtestsresultsrI   messagestackrM   i  )rf   rd   re   r   )rz   r9   r&   err_rawmsgs        r   rg   rg      s    "% 
"hhy"- 		"Fjj)G'4(kk),JG0DJGS)5Dz!		"
"     c                    t        j                  d      } | j                  dd       | j                  dd       | j                  dd	       | j                  d
d 	       | j                  dt        d       | j	                         }t        j                  t
        j                  d       t        |j                        j                         }t        |j                        j                         }t        |j                  xs d|j                         j                         }|j                  dd       |j                  dk7  rWt         j#                  d|       ddt%        |      d}|dz  j'                  t)        j*                  |dd      d       t,        S t/        |      }|sWt         j#                  d       dd|j                  d}|dz  j'                  t)        j*                  |dd      d       t,        S t         j#                  d t1        |             t3        ||||j                  |j4                        \  }}|j7                  d!|j                         |j7                  d"|d d#        |dz  j'                  t)        j*                  |dd      d       t         j#                  d$|j9                  d%      |       |S )&Nu7   task-2385 머지 전 자동 E2E 회귀 차단 게이트)descriptionz	--task-idT)requiredz--project-pathz--scenarios-dirz1/home/jay/workspace/tests/auto_e2e_gate/scenarios)defaultz--output-dirz	--timeouti,  )typer   z)[%(asctime)s] [%(levelname)s] %(message)s)levelformatz0/home/jay/workspace/memory/events/auto_e2e_gate/r1   InsuRou1   project_path=%s — InsuRo 아님 → skip (PASS)skip
not_insuro)r/   r0   r%   zresult.jsonFr   )ensure_asciiindentr?   r@   u>   InsuRo server/src/extension/public 변경 0건 → skip (PASS)no_relevant_changes)r/   r0   rl   u5   InsuRo 변경 감지: %d건 → 6 시나리오 실행rl   changes_detected2   u#   게이트 결과: status=%s exit=%dr/   )argparseArgumentParseradd_argumentint
parse_argsloggingbasicConfigINFOr   r%   resolverj   rk   rl   rV   rn   r   rZ   r   
write_textra   dumpsrh   r*   lenr{   r   
setdefaultrf   )	parserargsr%   rj   rk   r&   changes	exit_codepayloads	            r   mainr      su   $$1jkF
d3
(48
)3fg
5
#s;Dgll3^_))*224L++,446Mdooj+[\`\h\h[i)jkssuJTD1 H$GV"lCP\L]^	m	#//

6PU^_0`kr/s#L1GTU".CPTP\P\]	m	#//

6PU^_0`kr/s
KKGWV'mZQUQ]Q]_c_k_klIwy$,,/)73B<8-++

7q9G ,  KK5w{{87LiXr   __main__)r%   r   returnz	list[str])r%   r   rj   r   rk   r   rl   r   r=   r   r   ztuple[int, dict])rz   re   r   r   )r   r   )__doc__
__future__r   r   ra   r   rW   rQ   r   sysr\   pathlibr   rh   ri   rS   r#   rT   	getLoggerr   r*   r{   rg   r   __name__exit r   r   <module>r      s   	 #    	   
  		= 
		?	+,_
_
.1_
6F_
D(V zCHHTV r   