a '¡Dgdaã@sœddlZddlZddlZddlZddlmZddlmZmZmZddl m Z m Z m Z m Z mZddlmZddlmZmZe e¡ZdZGdd „d e jƒZdS) éN)Údatetime)ÚAnyÚDictÚOptional)ÚdistrosÚhelpersÚ lifecycleÚsubpÚutil)Ú HostnameConf)Ú PER_ALWAYSÚ PER_INSTANCEa7# This file is generated from information provided by the datasource. Changes # to it will not persist across an instance reboot. To disable cloud-init's # network configuration capabilities, write a file # /etc/cloud/cloud.cfg.d/99-disable-network-config.cfg with the following: # network: {config: disabled} csbeZdZdZdZdZdZdZdeedœiZ dZ d Z d d „Z d d „Z dDdd„Zejdœdd„Zdd„Zdd„Zdd„ZdEdd„Zdd„Zeeeedœdd „Zd!d"„ZdFd#d$„Zd%d&œd'd(„Zed)d*„ƒZed+œ‡fd,d-„ Z‡fd.d/„Z ed0œ‡fd1d2„ Z!‡fd3d4„Z"dG‡fd5d6„ Z#dHd9d:„Z$e%d;d<„ƒZ&e'dd=œeeed>œd?d@„ƒZ(e%ee)edAœdBdC„ƒZ*‡Z+S)IÚDistrozpy3-pipz/usr/share/bkeymaps/z&/etc/profile.d/50-cloud-init-locale.shz/etc/network/interfacesz /etc/shadowZeni)Zeni_pathZ eni_headerz /var/lib/dhcpzdhclient\.leasescCs6tj ||||¡t |¡|_d|_d|_d|d<dS)NzC.UTF-8ZalpineZsshdZ ssh_svcname)rrÚ__init__rZRunnersÚ_runnerÚdefault_localeZosfamily)ÚselfÚnameZcfgÚpaths©rúsù zDistro.apply_locale)ÚpkglistcCs| ¡|jd|ddS)NÚadd)Úpkgs)Úupdate_package_sourcesÚpackage_command)rr#rrrÚinstall_packagesQszDistro.install_packagescCsxd}z| |¡}Wn8tyJt |jdd¡}|r6nt d¡YdSYn0|sXtdƒ}| |¡t  |t |ƒd¡dS)NÚcreate_hostname_fileTz8create_hostname_file is False; hostname file not createdrr) Ú_read_hostname_confÚIOErrorr Zget_cfg_option_boolZ_cfgÚLOGÚinfor Z set_hostnamerÚstr)rÚhostnameÚfilenameÚconfr)rrrÚ_write_hostnameUs" ÿÿ  zDistro._write_hostnamecCs| |j¡}|j|fS©N)Ú_read_hostnameZhostname_conf_fn)rZ sys_hostnamerrrÚ_read_system_hostnameks zDistro._read_system_hostnamecCstt |¡ƒ}| ¡|Sr3)r r Úload_text_fileÚparse)rr0r1rrrr*oszDistro._read_hostname_confcCs8d}z| |¡}|j}Wnty*Yn0|s4|S|Sr3)r*r/r+)rr0Údefaultr/r1rrrr4ts   zDistro._read_hostnamecCsdS)Nz 127.0.1.1rrrrrÚ_get_localhost_ipszDistro._get_localhost_ip)ÚlayoutÚmodelÚvariantÚoptionscCsÒ|sd}t |¡t|ƒ‚tj |j|¡}tj |¡sPd|}t |¡t|ƒ‚|sjd}t |¡t|ƒ‚tj |d|¡}tj |¡s¢d|}t |¡t|ƒ‚|r°t  d¡|r¾t  d¡t   d||g¡dS) NzKeyboard layout not specified.z,Keyboard layout directory %s does not exist.zKeyboard variant not specified.z %s.bmap.gzz(Keyboard variant file %s does not exist.z+Keyboard model is ignored for Alpine Linux.z.Keyboard options are ignored for Alpine Linux.z setup-keymap) r,ÚerrorÚ RuntimeErrorÚosÚpathrÚ keymap_pathÚisdirÚisfileÚwarningr )rr:r;r<r=ÚmsgZkeymap_layout_pathZkeymap_variant_pathrrrÚ set_keymap‚s>  ÿÿ  ÿ ÿÿ   zDistro.set_keymapcCstj|| |¡ddS)N)ÚtzZtz_file)rZset_etc_timezoneZ _find_tz_file)rrHrrrÚ set_timezone¤szDistro.set_timezonecCsš|dur g}dg}| d¡|r6t|tƒr6| |¡n|rNt|tƒrN| |¡|r\| |¡|dkrr| ddg¡t d|¡}| |¡tj|dddS) NZapkz--quietZupgradez--update-cachez --availablez%s-%sF)Úcapture)ÚappendÚ isinstancer.ÚlistÚextendr Zexpand_package_listr )rÚcommandÚargsr%Úcmdr#rrrr'§s      zDistro.package_commandF)ÚforcecCs$|jjd|jdg|rtntddS)Nzupdate-sourcesÚupdate)Zfreq)rÚrunr'r r )rrRrrrr&Às  üzDistro.update_package_sourcescCs|jsddg|_|jS)z7Allow distro to determine the preferred ntp client listZchronyZntp)Z_preferred_ntp_clientsrrrrÚpreferred_ntp_clientsÈs zDistro.preferred_ntp_clients)Úreturnc sÂt |¡rt d|¡dSd|vr2t d¡|d=t d¡rPtƒj|fi|¤ŽS|  dd¡}dd g}d d d d ddœ}ddi}|  d¡}|röt |t ƒr |  d¡}n"t |tƒrÂtjd|›dddddd„|Dƒ}d |¡|d<|  d¡rö| |d¡|r2|r2|D]*}t |¡s| |¡t d||¡qd|vrLt |dƒ|d<gddddœ} t| ¡ƒD]˜\} } | |vrž| ržt | t ƒrž| || | g¡n^| | vrÞ| rÞt | t ƒrÞ| dkrÔ|   d¡| | <n| | | <n| |vrf| rf| || ¡qf|  d ¡s|  d¡r"| d!¡| |¡t d"|¡zt |¡Wn8tjy~} zt d#|¡| ‚WYd} ~ n d} ~ 00| dD]d} t d$| ¡zt d%|| g¡Wn<tjyè} z t td&|| ¡| ‚WYd} ~ n d} ~ 00qˆ| d'rtƒj|| d'dd(| d)}| d*}d}|j}zt |¡}Wn6tyl} zt d+|¡| ‚WYd} ~ n d} ~ 00d}| ¡D](}|  d,¡}|d-|krz|}q¤qz|r®d.}d.|d/<d.|d0<d.|d1<d2}|durt  !|¡t  !d3¡j"}t |ƒ|d4<|d.kr|d5}|d6}|dur<||d7<|d.kr4|d5}|d8}| #|d, |¡¡}t d9||¡ztj$||d:dd;Wn8t%yª} zt td<|¡| ‚WYd} ~ n d} ~ 00nt td=||¡dS)>zü Add a user to the system using standard tools On Alpine this may use either 'useradd' or 'adduser' depending on whether the 'shadow' package is installed. Returns False if user already exists, otherwise True. z!User %s already exists, skipping.FZ selinux_userz0Ignoring selinux_user parameter for Alpine LinuxZuseraddÚ create_groupsTZadduserz-Dz-gz-hz-Gz-sú-u)ZgecosÚhomedirÚ primary_groupÚshellÚuidÚsystemz-SÚgroupsú,z The user z) has a 'groups' config value of type dictz22.3z=Use a comma-delimited string or array instead: group1,group2.)Z deprecatedZdeprecated_versionZ extra_messagecSsg|] }| ¡‘qSr)Ústrip)Ú.0ÚgrrrÚ óz#Distro.add_user..rZz created group '%s' for user '%s'r\N)r^Ú expiredateÚinactiveÚpasswdZno_create_homez-HzAdding user %szFailed to create user %szAdding user to group %sÚaddgroupz!Failed to add user %s to group %srg)Zhashedrerfú&Failed to read %s file, file not foundú:rrééézpassword agingz 1970-01-01éz & zacct expiration dateézinactivity periodzUpdating %s for user %sÚw©ZomodeZ preserve_modeúFailed to update %s filezFailed to update %s for user %s)&r Úis_userr,r-rEr ÚwhichÚsuperÚadd_userÚpopÚgetrLr.ÚsplitÚdictrZ deprecaterrKÚis_groupÚ create_groupÚdebugÚsortedÚitemsrNÚProcessExecutionErrorÚlogexcZ set_passwdÚ shadow_fnr6ÚFileNotFoundErrorÚ splitlinesrZ fromisoformatÚdaysÚreplacerr+)rrÚkwargsrWZ adduser_cmdZ adduser_optsZ adduser_flagsr^ÚgroupZunsupported_busybox_valuesÚkeyÚvalÚeZ addn_grouprerfÚshadow_contentsÚ shadow_fileÚ original_lineÚlineÚnew_line_partsZ update_typer…©Ú __class__rrrvÐs     û     ü      üÿþý      ÿ ÿ  ÿ     ÿÿ     ÿÿ ÿzDistro.add_userc sštj d¡rdt d¡vr&tƒ |¡Sdd|g}z,tj|ddgd\}}t d|¡rZWd SWn8tj y”}zt   t d |¡|‚WYd }~n d }~00d S) zL Lock the password of a user, i.e., disable password logins ú/usr/bin/passwdÚbbsuidrgz-lré©Úrcszis already lockedTz&Failed to disable password for user %sN) r@rAÚislinkÚreadlinkruÚ lock_passwdr ÚreÚsearchr€r rr,)rrrQZ_outÚerrr‹r‘rrršªsÿ þ    zDistro.lock_passwd)rc sštj d¡rdt d¡vr&tƒ |¡Sdd|g}z,tj|ddgd\}}t d|¡rZWd SWn8tj y”}zt   t d |¡|‚WYd }~n d }~00d S) zM Unlock the password of a user, i.e., enable password logins r“r”rgrXrr•r–zis already unlockedTz%Failed to unlock password for user %sN) r@rAr˜r™ruÚ unlock_passwdr r›rœr€r rr,)rrrQÚ_rr‹r‘rrržÆsÿ þ    zDistro.unlock_passwdc s^tj d¡rdt d¡vr&tƒ |¡Sd}|j}zt |¡}Wn4t yr}zt   d|¡|‚WYd}~n d}~00d}|  ¡D].}|  d¡}|d|kr€t  d|¡|}q°q€|rL|ddkr>d|d<| |d |¡d ¡}t  d |¡ztj||d d d Wn8ty:}zt t d|¡|‚WYd}~n d}~00n t  d|¡nt t d|¡dS)Nr“r”rirjrz'Found /etc/shadow line matching user %séÚ0r•zExpiring password for user %srpTrqrrz'Password for user %s is already expiredzFailed to set 'expire' for %s)r@rAr˜r™ruÚ expire_passwdr‚r r6rƒr,rEr„ryr}r†rrr+r)rÚuserrŒrr‹rŽrrr‘rrr¢äsNÿ þ       ÿ ü zDistro.expire_passwdcsÐt d¡rtƒ ||¡Sd|g}|s(g}t |¡r@t d|¡n>zt |¡t d|¡Wn"tj y|t  td|¡Yn0t |ƒdkrÌ|D]<}t  |¡s¬t d||¡qŽt d||g¡t d||¡qŽdS) NZgroupaddrhz(Skipping creation of existing group '%s'zCreated new group %szFailed to create group %srzCUnable to add group member '%s' to group '%s'; user does not exist.zAdded user '%s' to group '%s') r rtrur|r r{r,rEr-r€rÚlenrs)rrÚmembersZ group_add_cmdÚmemberr‘rrr|s.     üzDistro.create_groupÚpoweroffÚnowc Csp|dg}|dkr|dg7}nPz| tt|ƒdƒ¡Wn4tyj}ztd|fƒ|‚WYd}~n d}~00|S)Nz-dr¨r¡é<z?power_state[delay] must be 'now' or '+m' (minutes). found '%s'.)rKr.ÚintÚ ValueErrorÚ TypeError)rÚmodeZdelayÚmessagerOr‹rrrÚshutdown_command@s ÿÿýzDistro.shutdown_commandcCsdS)z1 Alpine uses OpenRC, not systemd FrrrrrÚ uses_systemdZszDistro.uses_systemdr–)ÚactionÚserviceÚ extra_argsc Gs¢ddg}ddg}t|ƒ|dgt|ƒ|dgt|ƒd|gt|ƒd|gt|ƒ|dgt|ƒ|dgt|ƒ|dgt|ƒ|d gd œ}t||ƒ}tj|d |d S) a< Perform the requested action on a service. This handles OpenRC specific implementation details. OpenRC has two distinct commands relating to services, 'rc-service' and 'rc-update' and the order of their argument lists differ. May raise ProcessExecutionError z rc-servicez --nocolorz rc-updateÚstopÚstartÚdelr$ÚrestartÚstatus)r´rµÚdisableÚenabler·Úreloadz try-reloadr¸T)rJr—)rMr ) rr±r²r—r³Zinit_cmdZ update_cmdZcmdsrQrrrÚmanage_serviceas ø zDistro.manage_service)ÚblockdevrVcCsôtj |¡}| d¡rÔt t |¡j¡}t t |¡j¡}t d¡€}|D]j}|j  d¡rJt  |j¡}t  |j ¡rJt t |j¡j¡|krJt t |j¡j¡|krJtj |j¡}q¶qJWdƒn1sÊ0Y| d¡rðt  d||¡|SdS)aReturns underlying block device for a mapped device. If it is mapped, blockdev will usually take the form of /dev/mapper/some_name If blockdev is a symlink pointing to a /dev/dm-* device, return the device pointed to. Otherwise, return None. z /dev/mapperz/dev/zdm-Nz/dev/dm-z$%s is a mapped device pointing to %s)r@rAÚrealpathÚ startswithÚmajorÚstatÚst_rdevÚminorÚscandirrÚlstatÚS_ISBLKÚst_moder,r})r½r¾rÀrÃÚitZdeventryÚresrrrÚget_mapped_device}s2      ÿÿÿý$ ÿzDistro.get_mapped_device)N)N)NN)N)r§r¨N),Ú__name__Ú __module__Ú __qualname__Zpip_package_namerBrZnetwork_conf_fnr‚ÚNETWORK_FILE_HEADERZrenderer_configsZdhclient_lease_directoryZdhclient_lease_file_regexrrr"rZ PackageListr(r2r5r*r4r9r.rGrIr'r&ÚpropertyrUÚboolrvršržr¢r|r¯Ú staticmethodr°Ú classmethodr¼rrÊÚ __classcell__rrr‘rr sP ÿ   "  [  9#  ÿÿr)Zloggingr@r›rÁrÚtypingrrrZ cloudinitrrrr r Z"cloudinit.distros.parsers.hostnamer Zcloudinit.settingsr r Z getLoggerrËr,rÎrrrrrÚ s