܍~c ddlZddlZddlZddlZddlZddlmZddlmZm Z ddl m Z m Z m Z mZmZddlmZmZddlmZddlmZmZddlmZdd lmZdd lmZdd lmZdd lmZm Z dd l!m"Z"ddl#m$Z$ddl%m&Z&ddl'm(Z(dZ)dZ*dZ+dZ,e)e*e+gZ-dZ.dZ/dZ0dZ1dZ2dZ3dZ4dZ5ej6e7Z8ddfdd fd!d"fd#Z9e Gd$d%eZ:Gd&d'e;Z<Gd(d)e;Z=Gd*d+e;Z>dHd.Z?e2fd/Z@ed0gd1ZAed2d3d4gZBGd5de&ejC6ZDd7ZEd8eeDeFffd9ZGd:ZH dIdZKdJd@ZLGdAdBeMZNdCZOdDeDdEeFd8eIfdFZPdEeFd8eeDfdGZQdS)KN) namedtuple)Enumunique)AnyDictListOptionalTuple)dmiimporter)log)net type_utils) user_data)util) write_json)Distro) EventScope EventType) launch_index)Paths)CloudInitPickleMixin)eventsdisabledlocalrpass FILESYSTEMNETWORK DataSourcez|EXPERIMENTAL: The structure and format of content scoped under the 'ds' key may change in subsequent releases of cloud-init.zredacted for non-root user cloud-name_unsetunknownz aws-chinac|dkSNawscs r*?s 1:zaws-govc|dkSr$r&r's r)r*r*@s Q%Zr+z azure-chinac|dkS)Nazurer&r's r)r*r*As qG|r+)zcn-zus-gov-chinac2eZdZdZdZdZdZdZdZde fdZ d S) NetworkConfigSourcezb Represents the canonical list of network config sources that cloud-init knows about. cmdlineds system_cfgfallback initramfsreturnc|jSNvalueselfs r)__str__zNetworkConfigSource.__str__Rs zr+N) __name__ __module__ __qualname____doc__CMD_LINEDS SYSTEM_CFGFALLBACK INITRAMFSstrr>r&r+r)r1r1EsT H BJHIr+r1ceZdZdZdS)DatasourceUnpickleUserDataErrorzERaised when userdata is unable to be unpickled due to python upgradesNr?r@rArBr&r+r)rJrJVsOOOOr+rJceZdZdS)DataSourceNotFoundExceptionNr?r@rAr&r+r)rMrMZDr+rMceZdZdZdS)InvalidMetaDataExceptionz8Raised when metadata is broken, unavailable or disabled.NrKr&r+r)rQrQ^sBBBBr+rQr&ctj|}g}g}|D]\}}|r |dz|z}n|}||vs||vr||t |t rC|dr.|||dd||<t |trft|||} | | d| | d| ||<t||d<t||d<|S)zProcess all instance metadata cleaning it up for persisting as json. Strip ci-b64 prefix and catalog any 'base64_encoded_keys' as a list @return Dict copy of processed metadata. /zci-b64:rRbase64_encoded_keyssensitive_keys) copydeepcopyitemsappend isinstancerH startswithreplacedictprocess_instance_metadataextendpopsorted) metadatakey_pathrVmd_copyrU sens_keyskeyval sub_key_path return_vals r)r_r_bssmH%%GINN$$&&S  #c>C/LLL . LN$B$B   \ * * * c3   6CNN9$=$= 6  & &| 4 4 4;;y"55GCL c4  &2\>J & &z~~6K'L'L M M M   Z^^,<== > > >%GCL%+,?%@%@G !" &y 1 1G  Nr+c.|dgs|Stj|}|dD]R}|d}|}|D]1}t ||t r||dkr||}2|||<S|S)zRedact any sensitive keys from to provided metadata dictionary. Replace any keys values listed in 'sensitive_keys' with redact_value. rVrT)getrWrXsplitr[r^)rc redact_valuererd path_partsobjpaths r)redact_sensitive_keysrss <<(" - -mH%%GLL!122!!^^C((   D#d)T** tz"~/E/E$i D Nr+ URLParams)max_wait_secondstimeout_seconds num_retriessec_between_retriesDataSourceHostnamehostname is_defaultc feZdZUeZdZdZdZdZdZ dZ e j e j e je jfZee dfed<dZdZdZd ZejejejejejhiZejejhiZd e fd e fd ifd dddddf Z!eee"e#fdfed<dZ$dZ%ee"dfed<dZ&d Z'dIde(de)fdZ*de+ddfdZ,dZ-dZ.dJd Z/de0fd!Z1dKd#Z2de0fd$Z3d%Z4dLd&Z5d'Z6d(Z7e8d)Z9e8d*Z:e8d+Z;d,Ze8d/Z?d0Z@e8d1ZAd2ZBd3ZCd4ZDd5ZEd6ZFd7ZGd8ZHd9ZId:ZJe8d;ZKe8d<ZLd=ZMdMd>ZNd?ZOd@ePefdAZQd@ePede0fdBZRdCZSeTdNdDZUe8dEZVe8dFZWdGZXdHZYdS)Orz en_US.UTF-8_undefN.network_config_sourcesrl  ec2_metadata network_jsonrc)userdataN) userdata_rawN) vendordataN)vendordata_rawN) vendordata2N)vendordata2_rawNcached_attr_defaultsF) merged_cfgzsecurity-credentialssensitive_metadata_keysdistropathscN||_||_||_d|_i|_d|_d|_d|_d|_d|_ tj |jd|j fi|_ |j si|_ |s tj|j|_dS||_dS)N datasource)sys_cfgrrrrcrrrrrrget_cfg_by_pathdsnameds_cfgudUserDataProcessorud_proc)r=rrrrs r)__init__zDataSource.__init__s       "#* L<5r   { DK #/ ;;DLLL"DLLLr+ci_pkl_versionr7cht|dsd|_t|dsd|_t|dsd|_t|drZ|jU t |jdS#t $r/}td|t|d}~wwxYwdSdS)z(Perform deserialization fixes for Paths.rNrskip_hotplug_detectFrz:Unable to unpickle datasource: %s. Ignoring current cache.) hasattrrrrrrHAttributeErrorLOGdebugrJ)r=res r) _unpicklezDataSource._unpicklest]++ $#D t.// (#'D t233 -',D $ 4 $ $ ?)B  ?DM"""""! ? ? ? / 677Q>  ? ? ?)B)BsA44 B->*B((B-c*tj|Sr9robj_namer<s r)r>zDataSource.__str__3s"4(((r+c(|j}|}|j}|d}diddgd|d|dt |j|j|jd|jd |jd |d d d |d dd|d dd|jd|d|dd|d|d|ddd|d||dd|j|j |d|ddiS)z2Return a dictionary of standardized metadata keys.sys_infov1 _beta_keys subplatformavailability-zoneavailability_zonecloud_idr cloud_namerdistrdistro_versionrdistro_releaseplatformpublic_ssh_keyspython_versionpython instance-id instance_idkernel_releaseunamelocal-hostnamelocal_hostnamevariant)machineregionrsystem_platformr) get_hostnamerzget_instance_idrcanonical_cloud_idrr platform_typeget_public_ssh_keysr)r= instance_datarrrsysinfos r)_get_standardized_metadataz%DataSource._get_standardized_metadata6s**,,5**,,  2 + }o#%6$%6.OT[$2D dodo'&/!,!'&/!"4!'&/!"4D."4#;#;#=#=!'("3{ {!"!''"21"5#$!.%&!.'(#7+A.+#/#*:#6"9-1  r+r&c|jsdS|r|}n|j}|D]&\}}t||rt|||'|s d|_dSdS)zReset any cached metadata attributes to datasource defaults. @param attr_defaults: Optional tuple of (attr, value) pairs to set instead of cached_attr_defaults. NF) _dirty_cacherrsetattr)r= attr_defaults attr_values attributer;s r)clear_cached_attrszDataSource.clear_cached_attrs\s    F  4'KK3K + 0 0 IutY'' 0i/// & %D    & &r+cld|_|}|s|S||S)zDatasources implement _get_data to setup metadata and userdata_raw. Minimally, the datasource should return a boolean True on success. T)r _get_datapersist_instance_data)r= return_values r)get_datazDataSource.get_dataosA !~~''    ""$$$r+Tc6|rQtj|jjr(t ||jdt|drStj t|d}| dd| ddd|i}nwdd|j ii}t|dr&t|d}|tkr ||dd<t|d r&t|d }|tkr ||dd <t|dd <tj |j|d <d |d d <t!j|d <||| t!j|}t+t-j||j}n{#t2$r3}t4dt9|Yd}~dSd}~wt:$r3}t4dt9|Yd}~dSd}~wwxYw|jd} |ddd} tj |jj!d} t!j"| d| | dtj#| r tj$| } n| } t!j%| d| | d| | krt!j&| tO| |d|jd} tO| tQ|dS)aPProcess and write INSTANCE_JSON_FILE with all instance metadata. Replace any hyphens with underscores in key names for use in template processing. :param write_cache: boolean set True to persist obj.pkl when instance_link exists. @return True on successful write, False otherwise. obj_pkl_crawled_metadataz user-dataNz vendor-datar3 meta_datarr_docrzUMerged cloud-init system config from /etc/cloud/cloud.cfg and /etc/cloud/cloud.cfg.d/r)rVz'Error persisting instance-data.json: %sFinstance_data_sensitiverrnonezcloud-id- T)forcei)moder))osrrlexistsr instance_link pkl_store get_ipath_currrWrXgetattrrarcUNSETEXPERIMENTAL_TEXTrr system_infoupdater json_dumpsr_jsonloadsr TypeErrorrwarningrHUnicodeDecodeError get_runpathrmjoinrun_dir write_fileexistsrealpathsym_linkdel_filerrs)r= write_cachecrawled_metadatarrrcontentprocessed_datarjson_sensitive_filer cloud_id_fileprev_cloud_id_file json_files r)rz DataSource.persist_instance_data{s  A27??4:+CDD A dDJ44Y?? @ @ @ 4, - - G $}122     d 3 3 3   5 5 5!#34MM!K#?@Mt^,, G&t^<< 5((:FM$'7t^,, G&t^<< 5((:FM$'7&7 dF#&*mDL&A&A l# ' l#F+%)$4$6$6 j!T<<]KKLLL om44G6 7###;NN    KKA3q66 J J J55555!    KKA3q66 J J J55555 #j445NOO &**:v>> TZ%7DD  =55855(GGG 7>>- ( ( /!#!1!1-!@!@  !.  3333]$OOOO  . . M, - - -&UCCCCJ**?;; 93NCCDDDts$$|j}t jtd|jd|YnwxYw|j } t|jd|j }nD#t$r7t jtd|jd|YnwxYw|j } t|jd|j }nD#t$r7t jtd |jd|YnwxYwt||||S) zReturn the Datasource's preferred url_read parameters. Subclasses may override url_max_wait, url_timeout, url_retries. @return: A URLParams object with max_wait_seconds, timeout_seconds, num_retries. max_waitz6Config max_wait '%s' is not an int, using default '%s'rtimeoutz5Config timeout '%s' is not an int, using default '%s'retriesz5Config retries '%s' is not an int, using default '%s'rxzAConfig sec_between_retries '%s' is not an int, using default '%s') url_max_waitintrrm ValueErrorrlogexcr url_timeoutmax url_retries Exceptionurl_sec_between_retriesrt)r=rrrrxs r)get_url_paramszDataSource.get_url_paramssM$ 4;??:t7HIIJJHH    KH  ++       " !SDA87A8;B??ADD-E>FF -F::>G;:G;c|j1|j||_|r||jS|jSr9)rrprocessget_userdata_raw _filter_xdata)r= apply_filters r) get_userdatazDataSource.get_userdatasS =  L001F1F1H1HIIDM  5%%dm44 4}r+c|j1|j||_|jSr9)rrrget_vendordata_rawr<s r)get_vendordatazDataSource.get_vendordata s5 ? ""l2243J3J3L3LMMDOr+c|j1|j||_|jSr9)rrrget_vendordata2_rawr<s r)get_vendordata2zDataSource.get_vendordata2s8   ##|33D4L4L4N4NOOD r+c|j?tj|_|j td|j|jS)zADetermine the network interface used during local network config.Nz(Did not find a fallback interface on %s.)_fallback_interfacerfind_fallback_nicrrrr<s r)fallback_interfacezDataSource.fallback_interfacesO  # +'*'<'>'>D $'/ >''r+ct|ds|j|_|js|j|_|jS)N_platform_type)rrlowerr!r<s r)rzDataSource.platform_type"sUt-.. 6"&+"3"3"5"5D " 6"&+"3"3"5"5D ""r+ct|ds||_|js||_|jS)aReturn a string representing subplatform details for the datasource. This should be guidance for where the metadata is sourced. Examples of this on different clouds: ec2: metadata (http://169.254.169.254) openstack: configdrive (/dev/path) openstack: metadata (http://169.254.169.254) nocloud: seed-dir (/seed/dir/path) lxd: nocloud (/seed/dir/path) _subplatform)r_get_subplatformr$r<s r)rzDataSource.subplatform+sRt^,, 8 $ 5 5 7 7D   8 $ 5 5 7 7D   r+cVt|drdt|dzStS)z?Subclasses should implement to return a "slug (detail)" string.metadata_addressz metadata (%s))rrMETADATA_UNKNOWNr<s r)r%zDataSource._get_subplatform>s2 4+ , , G"WT3E%F%FF Fr+c|jr|jS|jr|jtr|jt}t |t r||_n||_t dtt|n+||_|jS)zReturn lowercase cloud name as determined by the datasource. Datasource can determine or define its own cloud product name in metadata. z5Ignoring metadata provided key %s: non-string type %s) _cloud_namercrmMETADATA_CLOUD_NAME_KEYr[rHr"_get_cloud_namerrtype)r=rs r)rzDataSource.cloud_nameDs   $# # = >T]../FGG >**+BCCJ*c** #-#3#3#5#5  #'#7#7#9#9#?#?#A#A  K+$$ $3355;;==D r+c|jS)zReturn the datasource name as it frequently matches cloud name. Should be overridden in subclasses which can run on multiple cloud names, such as DatasourceEc2. )rr<s r)r,zDataSource._get_cloud_name\s {r+cD|jsdSd|jvr |jdSdS)Nz launch-index)rcr<s r)rzDataSource.launch_indexds0} 4 T] * *=0 0tr+ctjtj|jg}|}|D]}||}|Sr9)rFilterrsafe_intapply)r= processed_udfiltersnew_udfs r)rzDataSource._filter_xdatalsP   d.? @ @ A A  % %AWWV__FF r+cdSNFr&r<s r)is_disconnectedzDataSource.is_disconnecteduur+c|jSr9)rr<s r)rzDataSource.get_userdata_rawys   r+c|jSr9)rr<s r)rzDataSource.get_vendordata_raw|s ""r+c|jSr9)rr<s r)rzDataSource.get_vendordata2_raws ##r+ciSr9r&r<s r)get_config_objzDataSource.get_config_objs r+cPt|jdS)Nz public-keys)normalize_pubkey_datarcrmr<s r)rzDataSource.get_public_ssh_keyss $T]%6%6}%E%EFFFr+cdS)a5Publish the public SSH host keys (found in /etc/ssh/*.pub). @param hostkeys: List of host key tuples (key_type, key_value), where key_type is the first field in the public key file (e.g. 'ssh-rsa') and key_value is the key itself (e.g. 'AAAAB3NzaC1y...'). Nr&)r=hostkeyss r)publish_host_keyszDataSource.publish_host_keyssr+cddi}|D]a\}}||s|D]C}d||t|d}tj|r|ccSDbdS)Nsd)vdxvdvtbz/dev/)rYr\lenrrrr)r= short_namemappingsnfromtlistntocands r) _remap_devicezDataSource._remap_devices ./&nn..  NUE((//   &)c:c%jjll+C+CD7>>$'' KKKKK  tr+cdSr9r&)r=_names r)device_name_to_devicez DataSource.device_name_to_devices tr+cj|j} |j}n#t$rYnwxYw|S)z, (str, bool). is_default is a bool and it's true only if hostname is localhost and was returned by util.get_hostname() as a default. This is used to differentiate with a user-defined localhost hostname. Optionally return (None, False) when metadata_only is True and local-hostname data is not available. localdomain localhostFrNT.rzip-%srr)rcrmryrrget_fqdn_from_hostsfindrHrnris_ipv4_address gethostbyaddrr]rKr) r=fqdn resolve_ip metadata_only defdomaindefhostdomainr{toksrz hosts_fqdnlhosts r)rzDataSource.get_hostnames&"  }# (DM$5$56F$G$G# ( <)$ ;;; D(**H;&&! 1(;;J ,jooc22Q66:,,S11 ,hmmC001448}}**3// , ),+M"23E"5)) (5-e44D?t99??3//DD#emmC&=&==>DD{{3'' t99q==AwHXXd122h''FFAwH  4Fi''"*((FF3H!(J777r+c8|j|S)N) data_source)rget_package_mirror_infor<s r)rsz"DataSource.get_package_mirror_infos{22t2DDDr+source_event_typesci}|D]f}|jD]J\}}||vrA||st||<|||Kg|Sr9)supported_update_eventsrYrmsetadd)r=rtsupported_eventsevent update_scope update_eventss r)get_supported_eventszDataSource.get_supported_eventss24' > >E-3355 > >M))+// ==?9<(6$\266u=== > r+c ||}|D]c\}}td|jdd|D|d|ztffd|r,||}|rdStd|dd|DdS) aRefresh cached metadata if the datasource supports this event. The datasource has a list of supported_update_events which trigger refreshing all cached metadata as well as refreshing the network configuration. @param source_event_types: List of EventTypes which may trigger a metadata update. @return True if the datasource did successfully update cached metadata due to source_event_type. z:Update datasource metadata and %s config due to events: %s, cg|] }|j Sr&r:.0rzs r) z;DataSource.update_metadata_if_supported..4sCCC55;CCCr+z _%s_configTz(Datasource %s not updated for events: %scg|] }|j Sr&r:rs r)rz;DataSource.update_metadata_if_supported..BsCCCuu{CCCr+F) r}rYrrr;rrrr)r=rtryscopematched_eventsresults r)update_metadata_if_supportedz'DataSource.update_metadata_if_supported s 445GHH%5%;%;%=%= F F !E> IIL  CCNCCCDD     # #lU&:E%B$D E E E E    # # % % %]]__F t 6  IICC0BCCC D D   ur+cdSr9r&)r=rs r)check_instance_idzDataSource.check_instance_idFr;r+c|t}|t}|D],}|||vr|cStd|||cS|S)Nz%invalid dsmode '%s', using default=%s)DSMODE_NETWORK VALID_DSMODESrr) candidatesdefaultvalid candidates r)_determine_dsmodezDataSource._determine_dsmodeJst ?$G =!E#  I E!!     ;Yr+cdSr9r&r<s r)network_configzDataSource.network_config`str+cdSr9r&r<s r)first_instance_bootzDataSource.first_instance_bootdsr+cdS)a(setup(is_new_instance) This is called before user-data and vendor-data have been processed. Unless the datasource has set mode to 'local', then networking per 'fallback' or per 'network_config' will have been written and brought up the OS at this point. Nr&)r=is_new_instances r)setupzDataSource.setuphs  r+cdS)aactivate(cfg, is_new_instance) This is called before the init_modules will be called but after the user-data and vendor-data have been fully processed. The cfg is fully up to date config, it contains a merged view of system config, datasource config, user config, vendor config. It should be used rather than the sys_cfg passed to __init__. is_new_instance is a boolean indicating if this is a new instance. Nr&)r=cfgrs r)activatezDataSource.activatess  r+r9)r&T)F)FFF)NN)Zr?r@rArdsmoderWrr*r!r$rr1rCrGrErDr~r __annotations__rr r rrrrBOOT_NEW_INSTANCEBOOT BOOT_LEGACYHOTPLUGrvdefault_update_eventsrrrHrrrr_ci_pkl_versionrrrrrr>rrboolrrrrrrrpropertyrrrr%rr,rrr:rrrr@rrErRrUrXrrrrrsrr}rr staticmethodrrrrrr&r+r)rrs F"NFKN L $%& ?E"5s":;LKK   ' N  !       '    R ! 9%c3h 45   L0U38_ O###u####.??????0)))$ $ $ L&&&&& $    FFFFP 4    :J:J:Jx    ((X(##X#!!X!$     X .XX!!!###$$$ GGG    KKXK++X+111 F8F8F8F8PEEE  tI     $"&y/$ $$$$L\*XX        r+) metaclasscg}|s|St|tr|St|ttfrt|St|t rj|D]U\}}t|tr|g}t|ttfr|D]}|r||V|Sr9)r[rH splitlineslistrwr^rYrZ) pubkey_datakeys_keynameklistpkeys r)rBrBs D  +s##(%%'''+c{++!K   +&& *!,!2!2!4!4 * * Xu%%% %$-- *!**D* D))) Kr+r7c t|||}d|D}t|vrdnd} td| |t ||D]\} } t jd| ddzd| d | d | d | | } | 5td | | |||} | tj gr1d| d | | _ | tj | fcdddcS dddn #1swxYwY#t$rtjtd| YwxYwdd|z}t%|)Nc6g|]}tj|Sr&r)rr7s r)rzfind_source..s#8881 #A&&888r+networkrz#Searching for %s data source in: %sz search-%srrRzsearching for z data from zno z data found from )name descriptionmessageparentz%Seeing if we can get any data from %szfound zGetting data from %s failedz4Did not find any data source, searched classes: (%s)r) list_sources DEP_NETWORKrrziprReportEventStackr]rrrrrrr rr rrM)rrrds_depscfg_listpkg_listreporterds_listds_namesrrclsmyrepsmsgs r) find_sourcersA8Wh77G88888H#w..99GDII3T8DDD7++AA c't||L"====;?44FF26$$=     A 9 9 A3GGGC//110199@DttTT$JEMz23778 9 9 9 9 9 9 9 9 9 99 9 9 9 9 9 9 9 9 9 9 9 9 9 9 9 A A A K:C @ @ @ @ @ A A499DD C &c * **s=D.A+D" D. D."D& &D.)D& *D..%EEcg}td||||D]}|ts t|}t j||dg\}}|std||D]J}t j|}t|d} | |} | r| | nK|S)NzLLooking for data source in: %s, via packages %s that matches dependencies %sget_datasource_listzDCould not import %s. Does the DataSource exist and is it importable?) rrr\ DS_PREFIXr find_moduleerror import_modulerr`) rdependsrsrc_listds_namem_locs _looked_locsm_locmodlistermatchess r)rrsHII 8 !!),, 4 ) 773G'3 X 56     II$      E(//CS"788FfWooG (((  Or+ system-uuidfieldc|sdStj|}|sdS||kSr9)r read_dmi_datar")rr dmi_values r)instance_id_matches_system_uuidrsO u!%((I u     )//"3"3 33r+c|st}|st}|tkr|tkr|S|StD].\}}|\}}||r||r|cS/|tkr|S|S)z@Lookup the canonical cloud-id for a given cloud_name and region.)r(CLOUD_ID_REGION_PREFIX_MAPrYr\)rrrprefix cloud_id_testr valid_clouds r)rrs &% "! !!! ) ) ) !;!A!A!C!C "/;   V $ $ Z)@)@ OOO%%% Or+Tc`|sdSt|tr|St|trtj|St|t r7|dur$t |ddStdtdt|z)aLdata: a loaded object (strings, arrays, dicts). return something suitable for cloudinit vendordata_raw. if data is: None: return None string: return string list: return data the list is then processed in UserDataProcessor dict: return convert_vendordata(data.get('cloud-init')) NTz cloud-initF)recursez'vendordata['cloud-init'] cannot be dictz$Unknown data type for vendordata: %s) r[rHrrWrXr^convert_vendordatarmrr-)datars r)rrs t$ $#}T"""$D d??%dhh|&<&>>uu {$UCCCCC  C;UCCCuu 4s %AAA%BBc|d} tj|d}nR#t$rE}tj|rt d||Yd}~nd}~wwxYw|sdS tj |S#t$rYdSt$rtj t d|YdSwxYw)zBUse pickle to deserialize a instance Datasource from a cache file.NF)decodezfailed loading pickle in %s: %sz#Failed loading pickled blob from %s) r load_filer rrrisfilerrrrrJr )rpickle_contentsrs r)pkl_loadrBsOE.u=== EEE 7>>%  E KK95! D D DE t|O,,, *tt  C>FFFtts, A*;A%%A*2B B;$B;:B;)rRr&)rr)RabcrWrrr collectionsrenumrrtypingrrrr r cloudinitr r r loggingrrrrrcloudinit.atomic_helperrcloudinit.distrosrcloudinit.eventrrcloudinit.filtersrcloudinit.helpersrcloudinit.persistencercloudinit.reportingrDSMODE_DISABLED DSMODE_LOCALr DSMODE_PASSrDEP_FILESYSTEMrrrREDACT_SENSITIVE_VALUEr+rr( getLoggerr?rrr1r rJrMrQr_rsrtryABCMetarrBrHrrrrrrIOErrorrrrrr&r+r)rs """"""33333333333333########$$$$$$%%%%%%%%%%%%%%......$$$$$$11111111******######666666&&&&&&   ,?   < 6'g!! -- .//033 4     $    PPPPPiPPP     )   CCCCCyCCC@2H$ J    Z [ [ [ [ [ %[ [ [ [ |:+ :s?++++J@, 4 4 4  4 4 4 4&JJJJ0     W   :cd$CHZ0r+