
    j                    v    d Z ddlm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mZmZmZmZmZ d Zd Zd Zd Zy)	u  tests.regression.test_autoset_cwd_canonical_lookup — task-2636.

Spec: memory/specs/system_callback_collector_canonical_root_spec_260523.md §8.

Reproduces the task-2635+1 incident: ANU collector spawn cwd lives under
``/home/jay/.cokacdir/workspace/autoset`` while the canonical artifact tree
is at ``/home/jay/workspace``. The collector MUST find the artifact via
canonical_root, never via getcwd().

Live subprocess calls are forbidden (monkeypatch os.getcwd).
    )annotationsN)CLASS_FOUNDCLASS_NOT_FOUNDdetect_context_mismatchfind_artifactresolve_canonical_rootresolve_pathc                   | dz  }|dz  dz  dz  }|j                   j                  d       |j                  t        j                  ddi             | dz  dz  d	z  j                  d       |j                  t        d
fd       dt        |      dd}t        |d      }|d   }d}||u }|slt        j                  d|fd||f      t        j                  |      t        j                  |      dz  }	dd|	iz  }
t        t        j                  |
            dx}x}}|d   }|t        k(  }|st        j                  d|fd|t        f      t        j                  |      dt        j                          v st        j"                  t              rt        j                  t              nddz  }dd|iz  }t        t        j                  |            dx}}|d   }t        |      }||k(  }|st        j                  d|fd||f      t        j                  |      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                  |      d"z  }
d#d$|
iz  }t        t        j                  |            dx}x}}t%        |t        | d%z        &      }|d'   }d}||u }|slt        j                  d|fd||f      t        j                  |      t        j                  |      dz  }	dd|	iz  }
t        t        j                  |
            dx}x}}|d(   }t        |      }||k(  }|st        j                  d|fd||f      t        j                  |      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                  |      d"z  }
d#d$|
iz  }t        t        j                  |            dx}x}}| 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                  |      d.z  }	t        t        j                  |	            dx}}|j)                  d/0      j+                         D cg c]'  }|j-                         rt        j.                  |      ) }}t1        |      }d1}||k(  }|st        j                  d|fd2||f      d3t        j                          v st        j"                  t0              rt        j                  t0              nd3d*t        j                          v st        j"                  |      rt        j                  |      nd*t        j                  |      t        j                  |      d4z  }
d#d$|
iz  }t        t        j                  |            dx}x}}|d5   d6   }t              }||k(  }|st        j                  d|fd||f      t        j                  |      d t        j                          v st        j"                  t              rt        j                  t              nd d7t        j                          v st        j"                        rt        j                        nd7t        j                  |      d"z  }
d#d$|
iz  }t        t        j                  |            dx}x}}|d5   d8   }t        |      }||k(  }|st        j                  d|fd||f      t        j                  |      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                  |      d"z  }
d#d$|
iz  }t        t        j                  |            dx}x}}yc c}w )9uE   The fresh-cwd false-negative incident — locked down by static gate.	workspacememoryreportsztask-2636-result.jsonTparentsokz	.cokacdirautosetgetcwdc                     t               S Nstr)fake_cwds   I/home/jay/workspace/tests/regression/test_autoset_cwd_canonical_lookup.py<lambda>zBtest_autoset_cwd_does_not_break_canonical_lookup.<locals>.<lambda>'   s    c(m     ztask-2636-tmz$memory/reports/task-2636-result.jsontask_idcanonical_rootresult_pathr   foundisz%(py1)s is %(py4)spy1py4assert %(py6)spy6Nclassification==z%(py1)s == %(py3)sr   r$   py3assert %(py5)spy5resolved_path)z0%(py1)s == %(py6)s
{%(py6)s = %(py3)s(%(py4)s)
}r   artifact)r$   r-   r%   r'   assert %(py8)spy8log_root)r4   mismatchr   	canonicaleventsz)callback_collector_context_mismatch.jsonlzAassert %(py4)s
{%(py4)s = %(py2)s
{%(py2)s = %(py0)s.exists
}()
}log_path)py0py2r%   zutf-8)encoding   z0%(py3)s
{%(py3)s = %(py0)s(%(py1)s)
} == %(py6)slenr9   r$   r-   r'   r   cwdr   canonical_root_resolved)parentmkdir
write_textjsondumpssetattrosr   r   
@pytest_ar_call_reprcompare	_safereprAssertionError_format_explanationr   @py_builtinslocals_should_repr_global_namer   exists	read_text
splitlinesstriploadsr>   )tmp_pathmonkeypatchr6   r1   enveloperesult@py_assert0@py_assert3@py_assert2@py_format5@py_format7@py_format4@py_format6@py_assert5@py_format9outr8   @py_assert1liner7   @py_assert4r   s                        @r   0test_autoset_cwd_does_not_break_canonical_lookuprg      sn    ;&I8#i/2IIHOO$'

D$<01 +%3i?HNN4N H&;< "i.=H 8]3F'?"d"?d""""?d"""?"""d""""""""#2#{2222#{222#222222{222{2222222/"3c(m3"m3333"m333"333333c333c333333(333(333m3333333 "(SJ9N5O
PCz?"d"?d""""?d"""?"""d""""""" 2C	N2 N2222 N222 222222C222C222222	222	222N2222222*$x/(:=hhH???88? &&&8CCE::< 	

4F 
 v;!;!;!33vv;!!9U,s8},},,,,},,,,,,,,,s,,,s,,,,,,8,,,8,,,},,,,,,,!9./A3y>A/>AAAA/>AAA/AAAAAA3AAA3AAAAAAyAAAyAAA>AAAAAAAs   2,cc                    |j                  t        d fd       d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	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}}t        |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 )Nr   c                      t         dz        S )N	elsewherer   )rV   s   r   r   zHtest_canonical_root_when_envelope_missing_uses_default.<locals>.<lambda>G   s    c([2H.I r   xmemory/x.json)r   r   z/home/jay/workspacer)   r=   r   envr?   r2   r3   r   z!/home/jay/workspace/memory/x.json)z%(py0)s == %(py3)sresolved)r9   r-   r.   r/   )rG   rH   r   rI   rJ   rN   rO   rP   rK   rL   rM   r	   )rV   rW   rm   r\   ra   rf   r^   rb   rn   rd   r_   r`   s   `           r   6test_canonical_root_when_envelope_missing_uses_defaultro   F   s   H&IJ/
:C!#&?*??&*?????&*???????!???!??????#???#???&???*????????C/H::8:::::8:::::::8:::8:::::::::::r   c                T   | dz  }|j                          | dz  j                          dz  }|j                  d       |j                  t        dfd       dt	        |      dd}t        |d	      }|d
   }d}||u }|st        j                  d|fd||f      t        j                  |      t        j                  |      dz  }	t        j                  d      dz   d|	iz  }
t        t        j                  |
            dx}x}}|d   }|t        k(  }|st        j                  d|fd|t        f      t        j                  |      dt        j                         v st        j                  t              rt        j                  t              nddz  }dd|iz  }t        t        j                  |            dx}}d}||z  }t	        |      }|d   }||v }|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                  |      t        j                  |      dz  }dd |iz  }t        t        j                  |            dx}x}x}x}}d}|z  }t	        |      }|d   }||v}|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                  |      t        j                  |      dz  }dd |iz  }t        t        j                  |            dx}x}x}x}}y)#a!  The COLLECTOR_LOOKUP_ORDER must never consult cwd as a primary root.

    We prove this by giving the canonical_root no artifact AND chdir-ing to a
    directory that DOES contain the artifact. The lookup must report NOT_FOUND
    instead of silently picking up the cwd-relative file.
    r6   rj   zresult.json{}r   c                     t               S r   r   )rj   s   r   r   zAtest_static_guard_no_cwd_in_primary_lookup_path.<locals>.<lambda>\   s    c)n r   rk   r   r   r   Fr    r"   r#   z)lookup must NOT use cwd as a primary rootz
>assert %(py6)sr'   Nr(   r)   r+   r   r,   r.   r/   lookup_attempts)in)z<%(py6)s
{%(py6)s = %(py0)s((%(py1)s / %(py3)s))
} in %(py9)sr   )r9   r$   r-   r'   py9zassert %(py11)spy11)not in)z@%(py6)s
{%(py6)s = %(py0)s((%(py1)s / %(py3)s))
} not in %(py9)s)rC   rD   rG   rH   r   r   rI   rJ   rK   _format_assertmsgrL   rM   r   rN   rO   rP   )rV   rW   r6   r1   rm   rc   rZ   r[   r\   r]   r^   r_   r`   rf   ra   @py_assert8@py_assert7@py_format10@py_format12rj   s                      @r   /test_static_guard_no_cwd_in_primary_lookup_pathr}   O   s    ;&IOO;&IOO=(HH&<= i.$C
 ]
+Cw<M5M<5 MMM<5MMM<MMM5MMM"MMMMMMMM 3 O3333 O333 333333O333O3333333(Cy=(C3()CS1B-CC)-CCCCC)-CCCCCCC3CCC3CCCCCCyCCCyCCC=CCC)CCC-CCCCCCCC(Gy=(G3()G5F1GG)1GGGGG)1GGGGGGG3GGG3GGGGGGyGGGyGGG=GGG)GGG1GGGGGGGGGr   c                    ddl }d }| j                  |d|       | j                  |d|       | j                  |d|       |dz  dz  }|j                  j                  d	
       |j	                  d       t        |      dd}t        |d      }|d   }d	}||u }	|	slt        j                  d|	fd||f      t        j                  |      t        j                  |      dz  }
dd|
iz  }t        t        j                  |            dx}x}	}y)u9   Defensive: lookup must not invoke subprocess (spec §10).r   Nc                     t        d      )Nz-subprocess.* must not be called during lookup)rL   )akws     r   _explodez8test_no_subprocess_calls_during_lookup.<locals>._explodeo   s    LMMr   runPopencheck_outputr   zx.jsonTr   rq   rl   )r   r   r   r   r    r"   r#   r&   r'   )
subprocessrG   rB   rC   rD   r   r   rI   rJ   rK   rL   rM   )rW   rV   r   r   r1   rm   rc   rZ   r[   r\   r]   r^   s               r   &test_no_subprocess_calls_during_lookupr   k   s    N 
E84
GX6
NH=("X-HOO$' ]?
KC
]
+Cw<4<4<4<4r   )__doc__
__future__r   builtinsrN   _pytest.assertion.rewrite	assertionrewriterI   rE   rH   utils.canonical_root_resolverr   r   r   r   r   r	   rg   ro   r}   r    r   r   <module>r      s:   
 #    	 'BT;H8 r   