
    Yf1>                       d Z ddlmZ ddlZddlZddlmZmZ ddlm	Z	 ddl
mZ ddlmZ ddlmZ dd	lmZ d
ZdZ ej                    r ed           ed          dZdZ G d de          Z G d de          ZdS )z'
Tests for L{twisted.python.lockfile}.
    )annotationsN)skipIf
skipUnless)NoReturn)lockfile)requireModule)platform)TestCaseF zwin32api.OpenProcess
pywintypesTzZOn windows, lockfile.kill is not implemented in the absence of win32api and/or pywintypes.c                     e Zd ZdZddZ e ej                    d          dd            ZddZ	 e ej                    d          dd	            Z
 eee          dd
            Z eee          dd            ZddZdS )	UtilTestszM
    Tests for the helper functions used to implement L{FilesystemLock}.
    returnNonec                    |                                  }t          j        d|           |                     t          t          j        d|          }|                     |j        t          j                   dS )z
        L{lockfile.symlink} raises L{OSError} with C{errno} set to L{EEXIST}
        when an attempt is made to create a symlink which already exists.
        fooN)mktempr   symlinkassertRaisesOSErrorassertEqualerrnoEEXISTselfnameexcs      L/var/www/html/env/lib/python3.11/site-packages/twisted/test/test_lockfile.pytest_symlinkEEXISTzUtilTests.test_symlinkEEXIST(   s`    
 {{}}%%%)95$GGEL11111    Bspecial rename EIO handling only necessary and correct on Windows.c                   |                                  }d
d}|                     t          d|           |                     t          t          j        |d          }|                     |j        t          j                   d	S )a<  
        L{lockfile.symlink} raises L{OSError} with C{errno} set to L{EIO} when
        the underlying L{rename} call fails with L{EIO}.

        Renaming a file on Windows may fail if the target of the rename is in
        the process of being deleted (directory deletion appears not to be
        atomic).
        srcstrdstr   r   c                6    t          t          j        d           Nr   r   EIOr#   r%   s     r   
fakeRenamez4UtilTests.test_symlinkEIOWindows.<locals>.fakeRenameA   s    %)T***r    renamer   Nr#   r$   r%   r$   r   r   )	r   patchr   r   IOErrorr   r   r   r)   )r   r   r+   r   s       r   test_symlinkEIOWindowsz UtilTests.test_symlinkEIOWindows2   sy     {{}}	+ 	+ 	+ 	+ 	

8Xz222)94GGEI.....r    c                    |                                  }|                     t          t          j        |          }|                     |j        t          j                   dS )z
        L{lockfile.readlink} raises L{OSError} with C{errno} set to L{ENOENT}
        when an attempt is made to read a symlink which does not exist.
        N)r   r   r   r   readlinkr   r   ENOENTr   s      r   test_readlinkENOENTzUtilTests.test_readlinkENOENTH   sK    
 {{}}):DAAEL11111r    Gspecial readlink EACCES handling only necessary and correct on Windows.c                   |                                  }d	d}|                     t          d|           |                     t          t          j        |          }|                     |j        t          j                   dS )
a\  
        L{lockfile.readlink} raises L{OSError} with C{errno} set to L{EACCES}
        on Windows when the underlying file open attempt fails with C{EACCES}.

        Opening a file on Windows may fail if the path is inside a directory
        which is in the process of being deleted (directory deletion appears
        not to be atomic).
        pathr$   moder   r   c                6    t          t          j        d           r'   r   r   EACCES)r7   r8   s     r   fakeOpenz6UtilTests.test_readlinkEACCESWindows.<locals>.fakeOpen`       %,---r    _openN)r7   r$   r8   r$   r   r   )	r   r.   r   r   r/   r2   r   r   r;   )r   r   r<   r   s       r   test_readlinkEACCESWindowsz$UtilTests.test_readlinkEACCESWindowsQ   sw     {{}}	. 	. 	. 	. 	

8Wh///):DAAEL11111r    c                R    t          j        t          j                    d           dS )z}
        L{lockfile.kill} returns without error if passed the PID of a
        process which exists and signal C{0}.
        r   N)r   killosgetpidr   s    r   	test_killzUtilTests.test_killg   s"     	bikk1%%%%%r    c                    |                      t          t          j        dd          }|                     |j        t
          j                   dS )z
        L{lockfile.kill} raises L{OSError} with errno of L{ESRCH} if
        passed a PID which does not correspond to any process.
        ir   N)r   r   r   rA   r   r   ESRCH)r   r   s     r   test_killESRCHzUtilTests.test_killESRCHo   s?     	1EEEK00000r    c                    |                      t          dd           t          j        |                                           }|                                 |                     |                                           dS )z
        Verify that when L{lockfile.kill} does end up as None (e.g. on Windows
        without pywin32), it doesn't end up being called and raising a
        L{TypeError}.
        rA   N)r.   r   FilesystemLockr   lockassertFalse)r   fls     r   test_noKillCallzUtilTests.test_noKillCally   sa     	

8VT***$T[[]]33
			#####r    Nr   r   )__name__
__module____qualname____doc__r   r   r	   	isWindowsr0   r4   r?   r   skipKillskipKillReasonrE   rH   rN    r    r   r   r   #   s4        2 2 2 2 ZO / / /	 /$2 2 2 2 ZT 2 2 2	 2$ VHn%%& & & &%& VHn%%1 1 1 &%1	$ 	$ 	$ 	$ 	$ 	$r    r   c                     e Zd ZddZddZ e ej                    d          dd            Zdd	Z	dd
Z
ddZddZddZ e ej                    d          dd            Z e ej                    d          dd            ZddZddZ e ej                    d          dd            ZddZddZddZddZddZdS ) LockingTestsr   intr   r   c                   dfd}|                      t          d|           |                                 }t          j        |          }|                     t
          |j                  }|                     |j                   d S )	Nsourcer$   destr   r   c                $    t          d           r'   )r   )r\   r]   r   s     r   fakeSymlinkz3LockingTests._symlinkErrorTest.<locals>.fakeSymlink   s    %&&&r    r   )r\   r$   r]   r$   r   r   )	r.   r   r   rJ   r   r   rK   r   r   )r   r   r_   lockfrK   r   s    `    r   _symlinkErrorTestzLockingTests._symlinkErrorTest   s    	' 	' 	' 	' 	' 	' 	

8Y444&u--33E*****r    c                D    |                      t          j                   dS )z
        An exception raised by C{symlink} other than C{EEXIST} is passed up to
        the caller of L{FilesystemLock.lock}.
        N)ra   r   ENOSYSrD   s    r   test_symlinkErrorzLockingTests.test_symlinkError   s     
 	u|,,,,,r    z9POSIX-specific error propagation not expected on Windows.c                    |                      t          j                   |                      t          j                   dS )a   
        An L{OSError} raised by C{symlink} on a POSIX platform with an errno of
        C{EACCES} or C{EIO} is passed to the caller of L{FilesystemLock.lock}.

        On POSIX, unlike on Windows, these are unexpected errors which cannot
        be handled by L{FilesystemLock}.
        N)ra   r   r;   r)   rD   s    r   test_symlinkErrorPOSIXz#LockingTests.test_symlinkErrorPOSIX   s6     	u|,,,uy)))))r    c                   |                                  }t          j        |          }|                     |                                           |                     |j                   |                     |j                   dS )z
        If the lock has never been held, it can be acquired and the C{clean}
        and C{locked} attributes are set to C{True}.
        N)r   r   rJ   
assertTruerK   cleanlockedr   r`   rK   s      r   test_cleanlyAcquirez LockingTests.test_cleanlyAcquire   si    
 &u--		$$$
###$$$$$r    c                   |                                  }t          j        |          }|                     |                                           |                                 |                     |j                   t          j        |          }|                     |                                           |                     |j                   |                     |j                   dS )z
        If a lock is released cleanly, it can be re-acquired and the C{clean}
        and C{locked} attributes are set to C{True}.
        N)	r   r   rJ   rh   rK   unlockrL   rj   ri   rk   s      r   test_cleanlyReleasez LockingTests.test_cleanlyRelease   s    
 &u--		$$$%%%&u--		$$$
###$$$$$r    c                N   |                                  }t          j        |          }|                     |                                           t          j        |          }|                     |                                           |                     |j                   dS )zK
        If a lock is currently locked, it cannot be locked again.
        N)r   r   rJ   rh   rK   rL   rj   )r   r`   	firstLock
secondLocks       r   test_cannotLockLockedz"LockingTests.test_cannotLockLocked   s     +E22		(())),U33
**+++*+++++r    c                &   dd
fd}|                                  }|                     t          d|           t          j        t	                    |           t          j        |          }|                     |                                           |                     |j	                   |                     |j
                   |                     t          j        |          t	          t          j                                         d	S )z
        If a lock was held by a process which no longer exists, it can be
        acquired, the C{clean} attribute is set to C{False}, and the
        C{locked} attribute is set to C{True}.
        i90  pidrZ   signalr   r   c                    |dk    rt          t          j        d           | k    rt          t          j        d           d S )Nr   r   r   EPERMrG   )ru   rv   owners     r   fakeKillz4LockingTests.test_uncleanlyAcquire.<locals>.fakeKill   s@    {{ek4000e||ek4000 |r    rA   Nru   rZ   rv   rZ   r   r   )r   r.   r   r   r$   rJ   rh   rK   rL   ri   rj   r   r2   rB   rC   )r   r{   r`   rK   rz   s       @r   test_uncleanlyAcquirez"LockingTests.test_uncleanlyAcquire   s     	1 	1 	1 	1 	1 	1 

8VX...UU+++&u--		$$$$$$$$$*5113ry{{3C3CDDDDDr    c                   dfd}|                      t          d|          dd
}|                      t          d|           |                                 t          j                  }t          j        t          d                     |                     |                                           |                     |j                   |                     |j	                   dS )z
        If the lock is initially held but then released before it can be
        examined to determine if the process which held it still exists, it is
        acquired and the C{clean} and C{locked} attributes are set to C{True}.
        r   r$   r   c                |    t          j                                                    t          j        |           S r'   )r   rmlinkrestorer2   )r   r`   readlinkPatchs    r   fakeReadlinkz?LockingTests.test_lockReleasedBeforeCheck.<locals>.fakeReadlink   s6    OE"""!!###$T***r    r2   ru   rZ   rv   r   c                    |dk    rt          t          j        d           | dk    rt          t          j        d           d S Nr   u  rx   ru   rv   s     r   r{   z;LockingTests.test_lockReleasedBeforeCheck.<locals>.fakeKill   ?    {{ek4000e||ek4000 |r    rA   r   N)r   r$   r   r$   r|   
r.   r   r   rJ   r   r$   rh   rK   ri   rj   )r   r   r{   rK   r`   r   s       @@r   test_lockReleasedBeforeCheckz)LockingTests.test_lockReleasedBeforeCheck   s    	+ 	+ 	+ 	+ 	+ 	+ 	+ 

8ZFF	1 	1 	1 	1 	

8VX...&u--UU+++		$$$
###$$$$$r    r!   c                   d	d}|                      t          d|           |                                 }t          j        |          }|                     |                                           |                     |j                   dS )
a  
        If the lock is released while an attempt is made to acquire
        it, the lock attempt fails and C{FilesystemLock.lock} returns
        C{False}.  This can happen on Windows when L{lockfile.symlink}
        fails with L{IOError} of C{EIO} because another process is in
        the middle of a call to L{os.rmdir} (implemented in terms of
        RemoveDirectory) which is not atomic.
        r#   r$   r%   r   r   c                6    t          t          j        d           r'   r(   r*   s     r   r_   zGLockingTests.test_lockReleasedDuringAcquireSymlink.<locals>.fakeSymlink  s     %)T***r    r   Nr-   )r.   r   r   rJ   rL   rK   rj   )r   r_   r`   rK   s       r   %test_lockReleasedDuringAcquireSymlinkz2LockingTests.test_lockReleasedDuringAcquireSymlink  s    	+ 	+ 	+ 	+
 	

8Y444&u--%%%%%%%%r    r5   c                \   d	d}|                      t          d|           |                                 }t          j        |          }t          j        t          d          |           |                     |                                           |                     |j                   dS )
z
        If the lock is initially held but is released while an attempt
        is made to acquire it, the lock attempt fails and
        L{FilesystemLock.lock} returns C{False}.
        r   r$   r   r   c                6    t          t          j        d           r'   r:   r   s    r   r   zILockingTests.test_lockReleasedDuringAcquireReadlink.<locals>.fakeReadlink+  s     %,---r    r2   r   Nr   r$   r   r   )	r.   r   r   rJ   r   r$   rL   rK   rj   )r   r   r`   rK   s       r   &test_lockReleasedDuringAcquireReadlinkz3LockingTests.test_lockReleasedDuringAcquireReadlink   s    	. 	. 	. 	. 	

8Z666&u--UU+++%%%%%%%%r    exceptionTypetype[OSError] | type[IOError]c                   dfd}|                      t          d|           |                                 }t          j        t	          d          |           t          j        |          }|                     |j                  }|                     |j	                   | 
                    |j                   d S )	Nr   r$   r   r   c                     d           r'   rW   )r   r   r   s    r   r   z5LockingTests._readlinkErrorTest.<locals>.fakeReadlink<  s    -t,,,r    r2   r   r   )r.   r   r   r   r$   rJ   r   rK   r   r   rL   rj   )r   r   r   r   r`   rK   r   s    ``    r   _readlinkErrorTestzLockingTests._readlinkErrorTest9  s    	- 	- 	- 	- 	- 	- 	- 	

8Z666 	UU+++&u--ty99E***%%%%%r    c                    |                      t          t          j                   |                      t          t          j                   dS )z
        An exception raised by C{readlink} other than C{ENOENT} is passed up to
        the caller of L{FilesystemLock.lock}.
        N)r   r   r   rc   r/   rD   s    r   test_readlinkErrorzLockingTests.test_readlinkErrorK  s:    
 	66666666r    c                    |                      t          t          j                   |                      t          t          j                   dS )z
        Any L{IOError} raised by C{readlink} on a POSIX platform passed to the
        caller of L{FilesystemLock.lock}.

        On POSIX, unlike on Windows, these are unexpected errors which cannot
        be handled by L{FilesystemLock}.
        N)r   r/   r   rc   r;   rD   s    r   test_readlinkErrorPOSIXz$LockingTests.test_readlinkErrorPOSIXS  s:     	66666666r    c                   dfd}|                      t          d|          dd
}|                      t          d|           |                                 t          j                  }t          j        t          d                     |                     |                                           |                     |j                   |                     |j	                   dS )z
        If a second process cleans up the lock after a first one checks the
        lock and finds that no process is holding it, the first process does
        not fail when it tries to clean up the lock.
        r   r$   r   r   c                |                                      t          j                   t          j        |           S r'   )r   r   r   )r   r`   rmlinkPatchs    r   
fakeRmlinkz?LockingTests.test_lockCleanedUpConcurrently.<locals>.fakeRmlinki  s5    !!!OE"""?4(((r    r   ru   rZ   rv   c                    |dk    rt          t          j        d           | dk    rt          t          j        d           d S r   rx   r   s     r   r{   z=LockingTests.test_lockCleanedUpConcurrently.<locals>.fakeKillr  r   r    rA   r   N)r   r$   r   r   r|   r   )r   r   r{   rK   r`   r   s       @@r   test_lockCleanedUpConcurrentlyz+LockingTests.test_lockCleanedUpConcurrentlyb  s    	) 	) 	) 	) 	) 	) 	) jj8Z@@	1 	1 	1 	1 	

8VX...&u--UU+++		$$$
###$$$$$r    c                   dd}|                      t          d|           dd}|                      t          d|           |                                 }t          j        t	          d          |           t          j        |          }|                     t          |j                  }| 	                    |j
        t          j                   |                     |j                   dS )z
        An exception raised by L{rmlink} other than C{ENOENT} is passed up
        to the caller of L{FilesystemLock.lock}.
        r   r$   r   r   c                6    t          t          j        d           r'   )r   r   rc   r   s    r   r   z1LockingTests.test_rmlinkError.<locals>.fakeRmlink  r=   r    r   ru   rZ   rv   r   c                    |dk    rt          t          j        d           | dk    rt          t          j        d           d S r   rx   r   s     r   r{   z/LockingTests.test_rmlinkError.<locals>.fakeKill  r   r    rA   r   Nr   r|   )r.   r   r   r   r$   rJ   r   r   rK   r   r   rc   rL   rj   )r   r   r{   r`   rK   r   s         r   test_rmlinkErrorzLockingTests.test_rmlinkError  s    	. 	. 	. 	. 	

8Xz222	1 	1 	1 	1 	

8VX... 	UU+++&u--33EL111%%%%%r    c                   d
d}|                      t          d|           |                                 }t          j        t	          d          |           t          j        |          }|                     t          |j                  }| 	                    |j
        t          j                   |                     |j                   d	S )z
        If L{kill} raises an exception other than L{OSError} with errno set to
        C{ESRCH}, the exception is passed up to the caller of
        L{FilesystemLock.lock}.
        ru   rZ   rv   r   r   c                6    t          t          j        d           r'   )r   r   ry   r   s     r   r{   z-LockingTests.test_killError.<locals>.fakeKill  s    %+t,,,r    rA   r   N)ru   rZ   rv   rZ   r   r   )r.   r   r   r   r$   rJ   r   r   rK   r   r   ry   rL   rj   )r   r{   r`   rK   r   s        r   test_killErrorzLockingTests.test_killError  s    	- 	- 	- 	- 	

8VX... 	UU+++&u--33EK000%%%%%r    c                   |                                  }t          j        t          t	          j                    dz             |           t          j        |          }|                     t          |j	                   dS )z
        L{FilesystemLock.unlock} raises L{ValueError} if called for a lock
        which is held by a different process.
           N)
r   r   r   r$   rB   rC   rJ   r   
ValueErrorrn   rk   s      r   test_unlockOtherzLockingTests.test_unlockOther  sd    
 RY[[1_--u555&u--*dk22222r    c                   |                                  }|                     t          j        |                     t          j        |          }|                     |                                           |                     t          j        |                     |                                 |                     t          j        |                     dS )zp
        L{isLocked} returns C{True} if the named lock is currently locked,
        C{False} otherwise.
        N)r   rL   r   isLockedrJ   rh   rK   rn   rk   s      r   test_isLockedzLockingTests.test_isLocked  s    
 *511222&u--		$$$)%00111*51122222r    N)r   rZ   r   r   rO   )r   r   r   rZ   r   r   )rP   rQ   rR   ra   rd   r   r	   rT   rf   rl   ro   rs   r}   r   r   r   r   r   r   r   r   r   r   r   r   rW   r    r   rY   rY      s0       	+ 	+ 	+ 	+- - - - VC 	* 	* 	*	 	*	% 	% 	% 	%% % % % 
, 
, 
, 
,E E E E2% % % %> ZO & & &	 &, ZT & & &	 &*& & & &$7 7 7 7 VC 	7 	7 	7	 	7% % % %>& & & &:& & & &,3 3 3 33 3 3 3 3 3r    rY   )rS   
__future__r   r   rB   unittestr   r   typing_extensionsr   twisted.pythonr   twisted.python.reflectr   twisted.python.runtimer	   twisted.trial.unittestr
   rU   rV   rT   r   rY   rW   r    r   <module>r      se  
  # " " " " "  				 ' ' ' ' ' ' ' ' & & & & & & # # # # # # 0 0 0 0 0 0 + + + + + + + + + + + +8 	
,--5M,''/< 	_$ _$ _$ _$ _$ _$ _$ _$DD3 D3 D3 D3 D38 D3 D3 D3 D3 D3r    