o
    x[h 2  ã                	   @   s.  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m	Z	 d dl
mZmZmZmZ d dlmZmZmZ d dlmZmZ d dlmZ d d	lmZmZmZ e e¡Zd
ddœddddœddddddgdœZG dd„ de	ƒZ G dd„ dej!ƒZ"G dd„ de"ƒZ#e#ej$ffe"ej$ej%ffgZ&deej! fdd„Z'dS )é    N)Ú	b64decode)Úsuppress)ÚEnum)ÚAnyÚListÚTupleÚUnion)ÚsourcesÚ
url_helperÚutil)Úfind_fallback_nicÚget_interfaces_by_mac)ÚEphemeralIPNetwork)Úget_dmi_configÚget_local_instance_idÚis_on_akamaizhttp://169.254.169.254zhttp://[fd00:a9fe:a9fe::1]©Úipv4Úipv6z	/v1/tokenz/v1/instancez/v1/user-data)ÚtokenÚmetadataÚuserdataTzf2:3)Ú	base_urlsÚpathsÚallow_local_stageÚallow_init_stageÚ
allow_dhcpÚ
allow_ipv4Ú
allow_ipv6Úpreferred_mac_prefixesc                   @   s   e Zd ZdZdZdZdZdS )ÚMetadataAvailabilityResultzj
    Used to indicate how this instance should behave based on the availability
    of metadata to it
    r   é   é   N)Ú__name__Ú
__module__Ú__qualname__Ú__doc__ÚNOT_AVAILABLEÚ	AVAILABLEÚDEFER© r*   r*   úD/usr/lib/python3/dist-packages/cloudinit/sources/DataSourceAkamai.pyr    -   s
    r    c                   @   s°   e Zd ZdZdZdd„ Zddededefdd	„Zde	fd
d„Z
de	fdd„Zde	fdd„Zdeeeeef ef  fdd„Zddedefdd„Zdefdd„Zdefdd„ZdS )ÚDataSourceAkamaiÚAkamaiFc                 C   sJ   t  d¡ tj | |||¡ tƒ | _t t	ƒ t 
|ddgi ¡tg¡| _d S )NzSetting up Akamai DataSourceÚ
datasourcer-   )ÚLOGÚdebugr	   Ú
DataSourceÚ__init__Údictr   r   Úmergemanydictr   Úget_cfg_by_pathÚBUILTIN_DS_CONFIGÚds_cfg)ÚselfÚsys_cfgÚdistror   r*   r*   r+   r2   <   s   
ýù
ÿzDataSourceAkamai.__init__Ú	path_nameÚuse_v6Úreturnc                 C   sZ   || j d vrtd |¡ƒ‚d}|s| j d sd}| j d | }| j d | }d ||¡S )zÛ
        Looks up the path for a given name and returns a full url for it.  If
        use_v6 is passed in, the IPv6 base url is used; otherwise the IPv4 url
        is used unless IPv4 is not allowed in ds_cfg
        r   zUnknown path name {}r   r   r   r   z{}{})r7   Ú
ValueErrorÚformat)r8   r;   r<   Úversion_keyÚbase_urlÚpathr*   r*   r+   Ú
_build_urlN   s   zDataSourceAkamai._build_urlc                 C   sN   | j d s
| j d r| j d s| j d st d¡ tjS | jr#|  ¡ S |  ¡ S )zŸ
        Returns whether metadata should be retrieved at this stage, at the next
        stage, or never, in the form of a MetadataAvailabilityResult.
        r   r   r   r   z*Configuration prohibits fetching metadata.)r7   r/   Úinfor    r'   Úlocal_stageÚ_should_fetch_data_localÚ_should_fetch_data_network©r8   r*   r*   r+   Ú_should_fetch_data`   s   ÿÿýü
z#DataSourceAkamai._should_fetch_datac                 C   sD   | j d st d¡ tjS | j d s| j d st d¡ tjS tjS )z‡
        Returns whether metadata should be retrieved during the local stage, or
        if it should wait for the init stage.
        r   z)Configuration prohibits local stage setupr   r   z9Configuration does not allow for ephemeral network setup.©r7   r/   rD   r    r)   r(   rH   r*   r*   r+   rF   t   s   

ÿz)DataSourceAkamai._should_fetch_data_localc                 C   s    | j d st d¡ tjS tjS )zS
        Returns whether metadata should be fetched during the init stage.
        r   z1Configuration does not allow for init stage setuprJ   rH   r*   r*   r+   rG   ‰   s   

z+DataSourceAkamai._should_fetch_data_networkc                    sú   g }| j ratƒ }d}| jd }| ¡ D ]\‰ }t‡ fdd„|D ƒƒr&|} nq|du r3t d¡ tƒ }g }| jd rH| t	| j
|ddd	�df¡ | jd
 r_| jd r_| t	| j
|dd�df¡ |S | jd rn| tƒ df¡ | jd
 r{| tƒ df¡ |S )zß
        Returns a list of context managers which should be tried when setting
        up a network context.  If we're running in init mode, this return a
        noop since networking should already be configured.
        Nr   c                    s   g | ]}ˆ   |¡‘qS r*   )Ú
startswith)Ú.0Úprefix©Úmacr*   r+   Ú
<listcomp>ª   s    zBDataSourceAkamai._get_network_context_managers.<locals>.<listcomp>zGFailed to find default interface, attempting DHCP on fallback interfacer   FTr   r   r   )r   )rE   r   r7   ÚitemsÚanyr/   Úwarningr   Úappendr   r:   Únoop)r8   Únetwork_context_managersÚ
interfacesÚ	interfaceÚpreferred_prefixesÚinfr*   rN   r+   Ú_get_network_context_managers”   sl   
þ
ÿüÿ
üùÿýúÿ
ðþÿ
þÿz.DataSourceAkamai._get_network_context_managersc              
   C   s6  z{t j| jd|d�ddddddid	�}|jd
kr"t d|j¡ W dS t|ƒ}t j| jd|d�dddd|dœd�}t t|ƒ¡| _	t j| jd|d�dddd|id�}t|ƒ| _
z
t| j
ƒ| _
W W dS  tjy{ } zt d|¡ W Y d}~W dS d}~ww  t jyš } zt d|r‹dnd|¡ W Y d}~dS d}~ww )z¶
        Runs through the sequence of requests necessary to retrieve our
        metadata and user data, creating a token for use in doing so, capturing
        the results.
        r   ©r<   ÚPUTé   r"   é   zMetadata-Token-Expiry-SecondsÚ300)Úrequest_methodÚtimeoutÚsec_betweenÚretriesÚheaderséÈ   z-Fetching token returned %s; not fetching dataTr   zapplication/json)ÚAcceptúMetadata-Token)rb   rc   rd   re   r   rh   z*Failed to base64 decode userdata due to %sNz1Failed to retrieve metadata using IPv%s due to %sÚ6Ú4F)r
   ÚreadurlrC   Úcoder/   rD   ÚstrÚjsonÚloadsr   Úuserdata_rawr   ÚbinasciiÚErrorrS   ÚUrlError)r8   r<   Útoken_responser   r   r   Úer*   r*   r+   Ú_fetch_metadataã   sj   ÿú

þþû
ÿû
	ó€ó
ý€÷z DataSourceAkamai._fetch_metadatac              	   C   sæ   t  d¡ tƒ st  d¡ dS tƒ }d|i| _|  ¡ }|tjkr3|tj	kr,t  d¡ dS t  d¡ dS |  
¡ }|D ]2\}}|�$ | j|d�}|r\| j d	|¡| jd< 	 W d
  ƒ  dS W d
  ƒ n1 sfw   Y  q9t  d¡ dS )zW
        Overrides _get_data in the DataSource class to actually retrieve data
        z#Getting data from Akamai DataSourcez#Not running on Akamai, not running.Fzinstance-idz5Metadata is not available, returning local data only.TzFConfigured not to fetch data at this stage; waiting for a later stage.r\   ÚidNzHFailed to contact metadata service, falling back to local metadata only.)r/   r0   r   rD   r   r   rI   r    r(   r'   r[   rv   ÚgetrS   )r8   Úlocal_instance_idÚavailabilityrV   Úmanagerr<   Údoner*   r*   r+   Ú	_get_data'  sJ   

ÿ

ÿÿ
þøïþ€ÿzDataSourceAkamai._get_datac                 C   s   t  |  ¡ d¡S )zj
        A local-only check to see if the instance id matches the id we see on
        the system
        zsystem-serial-number)r	   Úinstance_id_matches_system_uuidÚget_instance_id)r8   r9   r*   r*   r+   Úcheck_instance_id[  s   ÿz"DataSourceAkamai.check_instance_idN)F)r#   r$   r%   ÚdsnamerE   r2   rm   ÚboolrC   r    rI   rF   rG   r   r   r   r   r   r[   rv   r}   r€   r*   r*   r*   r+   r,   8   s    
þOD4r,   c                   @   s   e Zd ZdZdZdS )ÚDataSourceAkamaiLocalzÍ
    A subclass of DataSourceAkamai that runs the same functions, but during the
    init-local stage.  This allows configuring networking via cloud-init, as
    networking hasn't been configured yet.
    TN)r#   r$   r%   r&   rE   r*   r*   r*   r+   rƒ   e  s    rƒ   r=   c                 C   s   t  | t¡S )N)r	   Úlist_from_dependsÚdatasources)Údependsr*   r*   r+   Úget_datasource_list  s   r‡   )(rq   rn   ÚloggingÚbase64r   Ú
contextlibr   rU   Úenumr   Útypingr   r   r   r   Ú	cloudinitr	   r
   r   Úcloudinit.netr   r   Úcloudinit.net.ephemeralr   Ú cloudinit.sources.helpers.akamair   r   r   Ú	getLoggerr#   r/   r6   r    r1   r,   rƒ   ÚDEP_FILESYSTEMÚDEP_NETWORKr…   r‡   r*   r*   r*   r+   Ú<module>   sP    
þýÿî  /
þþü