
    xib                         d dl Z d dlmc mZ d dlmZ d dlZ G d dej                        Z	de
dee
eef   fdZdZ G d	 d
ej                        Zd Zd Zy)    N)FileSystemKeyMaterialStorec                   "    e Zd ZdZd Zd Zd Zy)InMemoryKmsClientzRThis is a mock class implementation of KmsClient, built for testing
    only.
    c                 d    t         j                  j                  |        |j                  | _        y)z%Create an InMemoryKmsClient instance.N)pe	KmsClient__init__custom_kms_confmaster_keys_map)selfconfigs     l/var/www/html/chatbot/card-advisor-bot/venv/lib/python3.12/site-packages/pyarrow/tests/parquet/encryption.pyr	   zInMemoryKmsClient.__init__   s"    
d#%55    c                     | j                   |   j                  d      }dj                  ||g      }t        j                  |      }|S )z`Not a secure cipher - the wrapped key
        is just the master key concatenated with key bytesutf-8r   )r   encodejoinbase64	b64encode)r   	key_bytesmaster_key_identifiermaster_key_byteswrapped_keyresults         r   wrap_keyzInMemoryKmsClient.wrap_key!   sM      //0EFMMhh 0)<=!!+.r   c                     || j                   vrt        d|      | j                   |   }t        j                  |      }|dd }|dd }||j	                  d      k(  r|S t        d||      )zGNot a secure cipher - just extract the key from
        the wrapped keyzUnknown master keyN   r   zIncorrect master key used)r   
ValueErrorr   	b64decodedecode)r   r   r   expected_master_keydecoded_wrapped_keyr   decrypted_keys          r   
unwrap_keyzInMemoryKmsClient.unwrap_key*   s     !(<(<<13HII"223HI$..{;.s3+BC0#3#:#:7#CC  4)=: 	:r   N)__name__
__module____qualname____doc__r	   r   r$    r   r   r   r      s    6
:r   r   r   returnc                     t        j                  d      }|j                  |       x}r9|j                         \  }}}t	        |      }t        j                  |      }|||fS t        d|       )zParses a wrapped key string into a tuple: (key id, version, key) given
    input in the form: <key id>:v<version>:<bas64 encoded key>z(.+?):v([0-9]+?):(.+)zCannot parse wrapped key)recompile	fullmatchgroupsintr   r   r   )r   ptnmidversionb64keykeys          r   parse_wrapped_keyr7   9   sm     **,
-CMM+&&q&hhjGVg,v&GS!!3[AAr   master_key_versionc                   V    e Zd ZdZddZedefd       Zdede	de	fdZ
d	e	de	defd
Zy)MockVersioningKmsClientae  This is a mock class implementation of KmsClient, built for testing
    only.

    During tests that involve CryptoFactory.rotate_master_keys, separate
    instances of this client will be created when writing, rotating keys, and
    reading back parquet data. To help unit tests verify that external key
    material was stored correctly at each step, this client wraps keys with a
    master_key_identifier and a version number. To ensure each client wraps
    with the correct version, the current version is persisted in the
    key_access_token attribute of the KmsConnectionConfig shared by all clients
    r*   Nc                 P    t         j                  j                  |        || _        y N)r   r   r	   connection_config)r   r=   s     r   r	   z MockVersioningKmsClient.__init__V   s    
d#!2r   c                 @    t        | j                  j                        S r<   )r0   r=   key_access_token)r   s    r   r8   z*MockVersioningKmsClient.master_key_versionZ   s    4))::;;r   r   r   c                 r    t        j                  |      j                  d      }| d| j                   d| S )Nr   z:v:)r   r   r    r8   )r   r   r   r5   s       r   r   z MockVersioningKmsClient.wrap_key^   s<    !!),33G<'(4+B+B*C1VHMMr   r   c                 H    t        |      \  }}}||k7  rt        d||      |S )Nz"Mismatched master key identifiers:)r7   r   )r   r   r   key_id_r6   s         r   r$   z"MockVersioningKmsClient.unwrap_keyb   s8     +;73**A#%:< <
r   )r*   N)r%   r&   r'   r(   r	   propertyr0   r8   bytesstrr   r$   r)   r   r   r:   r:   I   sf    
3 <C < <N% N N N $' ,1r   r:   c                 x    t        | d      5 }|j                  d      }|dk(  sJ 	 ddd       y# 1 sw Y   yxY w)zVerify that the file is encrypted by looking at its first 4 bytes.
    If it's the magic string PARE
    then this is a parquet with encrypted footer.rb   s   PAREN)openread)pathfile	magic_strs      r   verify_file_encryptedrP   m   s@     
dD	 $TIIaL	G###$ $ $s   09c                     t        j                  |       }t               }|j                         D ]"  }|j	                  |      }|||j
                  <   $ |S )zReads an external key material store given a parquet file path and
    returns a dict mapping master_key_id to KeyMaterial objects)r   for_filedictget_key_id_setget_key_materialmaster_key_id)rM   storekeysr3   key_materials        r   read_external_keys_to_dictrZ   w   sZ     '//5E6D""$ 8--b1+7\''(8 Kr   )r   pyarrow.parquet.encryptionparquet
encryptionr   pyarrow._parquet_encryptionr   r,   r   r   rG   tupler0   rF   r7   MASTER_KEY_VERSIONr:   rP   rZ   r)   r   r   <module>ra      sk   "  ' ' B 	: :D
B3 
B5c5+A 
B * !bll !H$r   