Your IP : 216.73.216.172


Current Path : /proc/self/root/lib/python3/dist-packages/certbot_apache/__pycache__/
Upload File :
Current File : //proc/self/root/lib/python3/dist-packages/certbot_apache/__pycache__/parser.cpython-38.pyc

U

���]��@s�dZddlZddlZddlZddlZddlZddlZddlZddlm	Z	m
Z
mZddlm
Z
ddlmZddlmZe�e�ZGdd�de�Zd	d
�Zdd�ZdS)
z@ApacheParser is a member object of the ApacheConfigurator class.�N)�Dict�List�Set)�errors)�os)�	constantsc@s�eZdZdZe�d�Zedddddg�Zdbd
d�Z	dd
�Z
dd�Zdd�Zdd�Z
dd�Zdd�Zdd�Zdd�Zdd�Zdd�Zd d!�Zd"d#�Zd$d%�Zd&d'�Zd(d)�Zd*d+�Zd,d-�Zd.d/�Zd0d1�Zdcd3d4�Zddd5d6�Zd7d8�Zd9d:�Z d;d<�Z!ded=d>�Z"dfd@dA�Z#dBdC�Z$dDdE�Z%dFdG�Z&dHdI�Z'dJdK�Z(dLdM�Z)dNdO�Z*dPdQ�Z+dRdS�Z,dTdU�Z-dVdW�Z.dXdY�Z/dZd[�Z0d\d]�Z1d^d_�Z2d`da�Z3dS)g�ApacheParsera�Class handles the fine details of parsing the Apache Configuration.

    .. todo:: Make parsing general... remove sites-available etc...

    :ivar str root: Normalized absolute path to the server root
        directory. Without trailing slash.
    :ivar set modules: All module names that are currently enabled.
    :ivar dict loc: Location to place directives, root - configuration origin,
        default - user config file, name - NameVirtualHost,

    z\$\{[^ \}]*}�*�?�\�[�]N���cCs�||_d|_|��|��s&t�d��t�|_i|_i|_	t
j�|�|_
d|��i|_|�|jd�|dkrv|��|��|��|j�|���t�|j�|_|r�|�t
j�|�d|j�d��|dkr�|jddd�r�t�d	��dS)
Nz�Apache plugin support requires libaugeas0 and augeas-lenses version 1.2.0 or higher, please make sure you have you have those installed.�rootr�/Zvhost_filesZDefineF)�excludezError parsing runtime variables)�configurator�aug�init_augeas�check_aug_versionrZNotSupportedError�set�modules�parser_paths�	variablesr�path�abspathr�_find_config_root�loc�
parse_file�update_runtime_variables�standardize_excl�
parse_modules�update�_set_locations�copy�deepcopy�existing_paths�option�find_dir�PluginError)�selfrZ	vhostroot�versionr�r.�7/usr/lib/python3/dist-packages/certbot_apache/parser.py�__init__%s4�
�zApacheParser.__init__cCsVzddl}Wntk
r*t�d��YnX|jtj|jj|jjB|jj	Bd�|_
dS)z' Initialize the actual Augeas instance rNzProblem in Augeas installation)Zloadpath�flags)�augeas�ImportErrorr�NoInstallationErrorZAugeasrZAUGEAS_LENS_DIRZNONEZNO_MODL_AUTOLOADZENABLE_SPANr)r,r2r.r.r/r[s���zApacheParser.init_augeasc	Csv|j�d�}|D]`}|j�|d�}|r||krd�|dt|�d�|j�|d�|j�|d��}t�|��qdS)	z�Verify Augeas can parse all of the lens files.

        :param str lens: lens to check for errors

        :raises .errors.PluginError: If there has been an error in parsing with
            the specified lens.

        �/augeas//errorz/lensz@There has been an error in parsing the file {0} on line {1}: {2}�
�z/linez/messageN)r�match�get�format�lenrr+)r,ZlensZerror_filesrZ	lens_path�msgr.r.r/�check_parsing_errorsls	��z!ApacheParser.check_parsing_errorscCsR|j�dd�z|j�d�}Wn"tk
r@|j�d�YdSX|j�d�|S)z� Checks that we have recent enough version of libaugeas.
        If augeas version is recent enough, it will support case insensitive
        regexp matchingz/test/path/testing/argZaRgUMeNTz,/test//*[self::arg=~regexp('argument', 'i')]z
/test/pathF)rrr8�RuntimeError�remove)r,�matchesr.r.r/r�s�zApacheParser.check_aug_versionc	Cs�|j�d�}|j�dd�|j�d�}z|j��Wn4ttfk
rh|�|�d|j_	t
�d��YnX|j�d|�|j�d�}t�}|r�|D]}|�|j�|�dd��q�|S)	a�Lists files that have modified Augeas DOM but the changes have not
        been written to the filesystem yet, used by `self.save()` and
        ApacheConfigurator to check the file state.

        :raises .errors.PluginError: If there was an error in Augeas, in
            an attempt to save the configuration, or an error creating a
            checkpoint

        :returns: `set` of unsaved files
        z/augeas/saveZnoopr5�z-Error saving files, check logs for more info.z/augeas/events/savedr7N)
rr9rr8�saver>�IOError�_log_save_errorsr�
save_notesrr+�add)r,Z
save_state�ex_errsZ
save_paths�
save_filesrr.r.r/�
unsaved_files�s$
�
zApacheParser.unsaved_filescCs&|��r"|jjd7_|j��dS)z�Makes sure that all Augeas dom changes are written to files to avoid
        loss of configuration directives when doing additional augeas parsing,
        causing a possible augeas.load() resulting dom reset
        z
(autosave)N)rIrrErB�r,r.r.r/�ensure_augeas_state�sz ApacheParser.ensure_augeas_statecCs>d|j_|j��|r:|D]}|j�d|�q|j��dS)z�Saves all changes to the configuration files.

        save() is called from ApacheConfigurator to handle the parser specific
        tasks of saving.

        :param list save_files: list of strings of file paths that we need to save.

        rAz/files/N)rrErrBr?�load)r,rHZsfr.r.r/rB�s	
zApacheParser.savecs6|j�d�}t�dd��fdd�|D��|jj�dS)zfLog errors due to bad Augeas save.

        :param list ex_errs: Existing errors before save

        r5z2Unable to save files: %s. Attempted Save Notes: %sz, c3s*|]"}|�kr|dt|�d�VqdS)r6r7N)r;)�.0�err�rGr.r/�	<genexpr>�s�z0ApacheParser._log_save_errors.<locals>.<genexpr>N)rr8�logger�error�joinrrE)r,rGZnew_errsr.rOr/rD�s
�zApacheParser._log_save_errorscCsd|�td�|�s`t�d|t|��|�t|�d|�tj�|�}tj�	|�}|j
�|g��|�dS)z�Add Include for a new configuration file if one does not exist

        :param str main_config: file path to main Apache config file
        :param str inc_path: path of file to include

        �IncludezAdding Include %s to %sN)
r*�case_irQ�debug�get_aug_path�add_dirrr�dirname�basenamer(�
setdefault�append)r,Zmain_configZinc_pathZnew_dirZnew_filer.r.r/�add_include�s��zApacheParser.add_includecCsH|d|jkr|j�|d�d|d|jkrD|j�d|d�dS)z%Shortcut for updating parser modules.�_moduleZmod_z.cN)rrF)r,�mod_namer.r.r/�add_mod�szApacheParser.add_modcCst�|_|��|��dS)zgReset the loaded modules list. This is called from cleanup to clear
        temporarily loaded modules.N)rr�update_modulesr#rJr.r.r/�
reset_modulesszApacheParser.reset_modulesc	Cs�t�}|�d�}t|�}d}t|�|kr�t|�}tj�||�D]b\}}|�|�}|�|�}|r�|r�|�|�|�t	j
�|�dd�d�q>t�
d|dd��q>q|j�|�dS)z�Iterates on the configuration until no new modules are loaded.

        ..todo:: This should be attempted to be done with a binary to avoid
            the iteration issue.  Else... parse and enable mods at same time.

        Z
LoadModule���N����cz8Could not read LoadModule directive from Augeas path: %sr7)rr*�iterr;�sixZmoves�zip�get_argrFrrrZrQrVrr$)	r,Zmodsr@�iteratorZ	prev_sizeZ
match_nameZmatch_filenamer_Zmod_filenamer.r.r/r#s&
�


 
�zApacheParser.parse_modulescCs|��|��|��dS)zAUpdate Includes, Defines and Includes from httpd config dump dataN)�update_defines�update_includesrarJr.r.r/r!$sz%ApacheParser.update_runtime_variablescCs�t�}|j�d�dddg}|�|d�}z|�d�Wntk
rJYdSX|D]@}|�d�dkrvt�d	�t	�
d
��|�d�}|d||d<qP||_dS)
zGet Defines from httpd process�ctl�-t�-DZDUMP_RUN_CFGzDefine: ([^ \n]*)N�=�z8Unexpected number of equal signs in runtime config dump.z&Error parsing Apache runtime variablesrr)
�dictrr)�parse_from_subprocessr?�
ValueError�countrQrRrr+�	partitionr)r,rZ
define_cmdr@r8�partsr.r.r/rk*s$�
�
zApacheParser.update_definescCsP|�d�}|j�d�dddg}|�|d�}|rL|D]}|�|�s2|�|�q2dS)z>Get includes from httpd process, and add them to DOM if neededrTrmrnroZ
DUMP_INCLUDESz\(.*\) (.*)N)r*rr)rs�parsed_in_currentr )r,�_Zinc_cmdr@�ir.r.r/rlAs
�
zApacheParser.update_includescCs<|j�d�dddg}|�|d�}|D]}|�|���q$dS)z:Get loaded modules from httpd process, and add them to DOMrmrnroZDUMP_MODULESz(.*)_moduleN)rr)rsr`�strip)r,Zmod_cmdr@�modr.r.r/raQs�zApacheParser.update_modulescCs|�|�}t�|��|�S)z�Get values from stdout of subprocess command

        :param list command: Command to run
        :param str regexp: Regexp for parsing

        :returns: list parsed from command output
        :rtype: list

        )�_get_runtime_cfg�re�compile�findall)r,�commandZregexp�stdoutr.r.r/rsZs

z"ApacheParser.parse_from_subprocessc	Cs�z&tj|tjtjdd�}|��\}}Wn8ttfk
r^t�d|tj	�t
�d�|���YnX|j
dkr�t�d|�t
�d��|S)zwGet runtime configuration info.
        :param command: Command to run

        :returns: stdout from command

        T)r��stderrZuniversal_newlinesz2Error running command %s for runtime parameters!%sz-Error accessing loaded Apache parameters: {0}rz$Error in checking parameter list: %sz^Apache is unable to check whether or not the module is loaded because Apache is misconfigured.)�
subprocess�Popen�PIPEZcommunicate�OSErrorrtrQrRr�lineseprZMisconfigurationErrorr:�
returncodeZwarning)r,r��procr�r�r.r.r/r}gs2����

�zApacheParser._get_runtime_cfgcCs�g}|dkr@t|�D](\}}|�d�r|�||dd��qnjt|�D]`\}}|�d|�rH|t|�dks�||d�d|d�sH|�||dtd|���qH|S)aFilter out directives with specific number of arguments.

        This function makes the assumption that all related arguments are given
        in order.  Thus /files/apache/directive[5]/arg[2] must come immediately
        after /files/apache/directive[5]/arg[1]. Runs in 1 linear pass.

        :param string matches: Matches of all directives with arg nodes
        :param int args: Number of args you would like to filter

        :returns: List of directives that contain # of arguments.
            (arg is stripped off)

        rq�/argN����/arg[%d])�	enumerate�endswithr\r;)r,r@�argsZfilteredrzr8r.r.r/�filter_args_num�s
��"zApacheParser.filter_args_numcCs�|�|d�}|j�|ddd�|d}|j�||�t|�dkrZ|j�|d|d�n,t|�D]"\}}|j�d	||df|�qbd
S)a�Adds directive and value to IfMod ssl block.

        Adds given directive and value along configuration path within
        an IfMod mod_ssl.c block.  If the IfMod block does not exist in
        the file, it is created.

        :param str aug_conf_path: Desired Augeas config path to add directive
        :param str directive: Directive you would like to add, e.g. Listen
        :param args: Values of the directive; str "443" or list of str
        :type args: list

        z	mod_ssl.c�arg�	directiveFzdirective[1]rqr�rz
%s/arg[%d]N)�	get_ifmodr�insertrr;r�)r,�
aug_conf_pathr�r�Zif_mod_pathZnvh_pathrzr�r.r.r/�add_dir_to_ifmodssl�sz ApacheParser.add_dir_to_ifmodsslFcCs8|j�d||f�}|s&|�|||�S|d�d�dS)aReturns the path to <IfMod mod> and creates one if it doesn't exist.

        :param str aug_conf_path: Augeas configuration path
        :param str mod: module ie. mod_ssl.c
        :param bool beginning: If the IfModule should be created to the beginning
            of augeas path DOM tree.

        :returns: Augeas path of the requested IfModule directive that pre-existed
            or was created during the process. The path may be dynamic,
            i.e. .../IfModule[last()]
        :rtype: str

        z%s/IfModule/*[self::arg='%s']rr�)rr8�create_ifmod�
rpartition)r,r�r|�	beginningZif_modsr.r.r/r��s�zApacheParser.get_ifmodcCsn|r0d�|�}|j�d�|�dd�d�|�}n,d�|�}d�|�}|j�|d�d	�|�}|j�||�|S)
a�Creates a new <IfMod mod> and returns its path.

        :param str aug_conf_path: Augeas configuration path
        :param str mod: module ie. mod_ssl.c
        :param bool beginning: If the IfModule should be created to the beginning
            of augeas path DOM tree.

        :returns: Augeas path of the newly created IfModule directive.
            The path may be dynamic, i.e. .../IfModule[last()]
        :rtype: str

        z{}/IfModule[1]/argz{}/directive[1]ZIfModuleTz{}/IfModule[1]/z{}/IfModule[last() + 1]z{}/IfModule[last()]/argrAz{}/IfModule[last()]/)r:rr�r)r,r�r|r�Z
c_path_argZretpathZc_pathr.r.r/r��s

�


zApacheParser.create_ifmodcCs^|j�|d|�t|t�rHt|d�D]\}}|j�d||f|�q&n|j�|d|�dS)a�Appends directive to the end fo the file given by aug_conf_path.

        .. note:: Not added to AugeasConfigurator because it may depend
            on the lens

        :param str aug_conf_path: Augeas configuration path to add directive
        :param str directive: Directive to add
        :param args: Value of the directive. ie. Listen 443, 443 is arg
        :type args: list or str

        z/directive[last() + 1]rqz%s/directive[last()]/arg[%d]z/directive[last()]/argN)rr�
isinstance�listr�)r,r�r�r�rz�valuer.r.r/rX�s

�zApacheParser.add_dircCsr|d}|j�|dd�|j�||�t|t�r\t|d�D]\}}|j�|d||�q:n|j�|d|�dS)a)Adds the directive to the beginning of defined aug_conf_path.

        :param str aug_conf_path: Augeas configuration path to add directive
        :param str dirname: Directive to add
        :param args: Value of the directive. ie. Listen 443, 443 is arg
        :type args: list or str
        z
/directive[1]r�Trqr�r�N)rr�rr�r�r�)r,r�rYr�Z	first_dirrzr�r.r.r/�add_dir_beginnings
zApacheParser.add_dir_beginningcCs|j�|d|�dS)z�Adds the comment to the augeas path

        :param str aug_conf_path: Augeas configuration path to add directive
        :param str comment: Comment content

        z/#comment[last() + 1]N)rr)r,r��commentr.r.r/�add_commentszApacheParser.add_commentcCsR|st|j�}|j�d|�}g}|D]&}|j�|�}|r&||kr&|�|�q&|S)aFinds a comment with specified content from the provided DOM path

        :param str arg: Comment content to search
        :param str start: Beginning Augeas path to begin looking

        :returns: List of augeas paths containing the comment content
        :rtype: list

        z%s//*[label() = '#comment'])rWrrr8r9r\)r,r��startZcommentsZresultsr�Z	c_contentr.r.r/�
find_commentss

zApacheParser.find_commentsTc
Cs�|st|jd�}dt|�td�td�f}|j�d||f�}|rN|�|�}|dkr\d}ndt|�}g}|D]l}	|j�|	���}
|
d	ks�|
d
kr�|�|�	|||�
|�|	d��|��|
|��krp|�|j�|	|��qp|S)a	Finds directive in the configuration.

        Recursively searches through config files to find directives
        Directives should be in the form of a case insensitive regex currently

        .. todo:: arg should probably be a list
        .. todo:: arg search currently only supports direct matching. It does
            not handle the case of variables or quoted arguments. This should
            be adapted to use a generic search for the directive and then do a
            case-insensitive self.get_arg filter

        Note: Augeas is inherently case sensitive while Apache is case
        insensitive.  Augeas 1.0 allows case insensitive regexes like
        regexp(/Listen/, "i"), however the version currently supported
        by Ubuntu 0.10 does not.  Thus I have included my own case insensitive
        transformation by calling case_i() on everything to maintain
        compatibility.

        :param str directive: Directive to look for
        :param arg: Specific value directive must have, None if all should
                    be considered
        :type arg: str or None

        :param str start: Beginning Augeas path to begin looking
        :param bool exclude: Whether or not to exclude directives based on
            variables and enabled modules

        rz(%s)|(%s)|(%s)rTZIncludeOptionalz$%s//*[self::directive=~regexp('%s')]Nr�z/*[self::arg=~regexp('%s')]ZincludeZincludeoptional)rWrrUrr8�
_exclude_dirsr9�lower�extendr*�_get_include_pathri)r,r�r�r�rZregexr@Z
arg_suffixZordered_matchesr8Zdir_r.r.r/r*4s6�
�
�zApacheParser.find_dircs6|ddkr|d}�j�|d�}�fdd�|D�S)z�
        Tries to fetch all arguments for a directive. See get_arg.

        Note that if match is an ancestor node, it returns all names of
        child directives as well as the list of arguments.

        rcrr	csg|]}��|��qSr.)ri)rMr�rJr.r/�
<listcomp>�sz-ApacheParser.get_all_args.<locals>.<listcomp>)rr8)r,r8Zallargsr.rJr/�get_all_args�s	zApacheParser.get_all_argsc	Csz|j�|�}|sdS|�d�}tj�|�}|D]F}z|�||j|dd��}Wq.tk
rrt	�
d|��Yq.Xq.|S)z�Uses augeas.get to get argument value and interprets result.

        This also converts all variables and parameters appropriately.

        N�'"rrczError Parsing variable: %s)rr9r{r�arg_var_interpreterr��replacer�KeyErrorrr+)r,r8r�r�varr.r.r/ri�s
zApacheParser.get_argcCsJd|jfd|jfg}g}|D](}|D]}|�||�s$qq$|�|�q|S)z>Exclude directives that are not loaded into the configuration.ZifmoduleZifdefine)rr�_pass_filterr\)r,r@�filtersZ
valid_matchesr8�filter_r.r.r/r��szApacheParser._exclude_dirscCs�|��}|�|d�}|dkr�|�d|�}|j�|d|�d�}|�d�rf|dd�|dkrvdSn||dkrvdS|�|d|�}qd	S)
z�Determine if directive passes a filter.

        :param str match: Augeas path
        :param list filter: list of tuples of form
            [("lowercase if directive", set of relevant parameters)]

        rrcrNr��!rqFT)r��findrr9�
startswith)r,r8r�Zmatch_lZlast_match_idxZ	end_of_ifZ
expressionr.r.r/r��s
zApacheParser._pass_filtercCs�|�d�}|�d�s.tj�tj�|j|��}ntj�|�}tj�|�r\|�tj�|d��n
|�|�|�	d�}t
|�D],\}}tdd�|D��rxd|�|�||<qxd�|�}t
|�S)a@Converts an Apache Include directive into Augeas path.

        Converts an Apache Include directive argument into an Augeas
        searchable path

        .. todo:: convert to use os.path.join()

        :param str arg: Argument of Include directive

        :returns: Augeas path string
        :rtype: str

        r�rr	css|]}|tjkVqdS)N)r�
fnmatch_chars)rM�charr.r.r/rPsz1ApacheParser._get_include_path.<locals>.<genexpr>z* [label()=~regexp('%s')])r{r�rr�normpathrSr�isdirr �splitr��any�
fnmatch_to_rerW)r,r�Z	split_arg�idxr�r.r.r/r��s



�

zApacheParser._get_include_pathcCs.tjdkrt�|�dd�St�|�dd�S)a�Method converts Apache's basic fnmatch to regular expression.

        Assumption - Configs are assumed to be well-formed and only writable by
        privileged users.

        https://apr.apache.org/docs/apr/2.0/apr__fnmatch_8h_source.html
        http://apache2.sourcearchive.com/documentation/2.2.16-6/apr__fnmatch_8h_source.html

        :param str clean_fn_match: Apache style filename match, like globs

        :returns: regex suitable for augeas
        :rtype: str

        )�r7Ni����r���)�sys�version_info�fnmatch�	translate)r,Zclean_fn_matchr.r.r/r�s
zApacheParser.fnmatch_to_recCsT|�|�\}}|��|rP|j�d|�}|sP|r<|�|�|�|�|j��dS)z�Parse file with Augeas

        Checks to see if file_path is parsed by Augeas
        If filepath isn't parsed, the file is added and Augeas is reloaded

        :param str filepath: Apache config file path

        z&/augeas/load/Httpd['%s' =~ glob(incl)]N)�_check_path_actionsrKrr8�_remove_httpd_transform�_add_httpd_transformrL)r,�filepath�use_new�
remove_oldZinc_testr.r.r/r  s	�

zApacheParser.parse_filecCs|�||j�S)a<Checks if the file path is parsed by current Augeas parser config
        ie. returns True if the file is found on a path that's found in live
        Augeas configuration.

        :param str filep: Path to match

        :returns: True if file is parsed in existing configuration tree
        :rtype: bool
        )�_parsed_by_parser_pathsr�r,�filepr.r.r/rx;s
zApacheParser.parsed_in_currentcCs|�||j�S)a[Checks if the file path is parsed by existing Apache config.
        ie. returns True if the file is found on a path that matches Include or
        IncludeOptional statement in the Apache configuration.

        :param str filep: Path to match

        :returns: True if file is parsed in existing configuration tree
        :rtype: bool
        )r�r(r�r.r.r/�parsed_in_originalGs
zApacheParser.parsed_in_originalc	Cs>|��D]0}||D]"}t�|tj�||��rdSqqdS)znHelper function that searches through provided paths and returns
        True if file path is found in the setTF)�keysr�rrrS)r,r��pathsZ	directory�filenamer.r.r/r�Ss
z$ApacheParser._parsed_by_parser_pathscCsbz<tj�|�}|jtj�|�}d|kr.d}nd}|dk}Wntk
rXd}d}YnX||fS)aLDetermine actions to take with a new augeas path

        This helper function will return a tuple that defines
        if we should try to append the new filepath to augeas
        parser paths, and / or remove the old one with more
        narrow matching.

        :param str filepath: filepath to check the actions for

        r	FT)rrrZrrYr�)r,r�Znew_file_matchZexisting_matchesr�r�r.r.r/r�\s
z ApacheParser._check_path_actionscCsd|jtj�|�}tj�|�}|D]0}|d|}|j�d|�}|j�|d�q"|j�|�dS)z[Remove path from Augeas transform

        :param str filepath: filepath to remove
        rz!/augeas/load/Httpd/incl [. ='%s']rN)rrrrYrr8r?�pop)r,r�Zremove_basenamesZremove_dirname�nameZremove_pathZ
remove_incr.r.r/r�us�z$ApacheParser._remove_httpd_transformcCs�|j�d�}|r4|j�|ddd�|j�d|�n|j�dd�|j�d|�z$|jtj�|��tj�	|��Wn0t
k
r�tj�	|�g|jtj�|�<YnXd	S)
a"Add a transform to Augeas.

        This function will correctly add a transform to augeas
        The existing augeas.add_transform in python doesn't seem to work for
        Travis CI as it loads in libaugeas.so.0.10.0

        :param str incl: filepath to include for transform

        z /augeas/load/Httpd/incl [last()]r�inclFz/augeas/load/Httpd/incl[last()]z/augeas/load/Httpd/lensz	Httpd.lnsz/augeas/load/Httpd/inclN)rr8r�rrrrrYr\rZr�)r,r�Zlast_includer.r.r/r��s

�
�z!ApacheParser._add_httpd_transformcCszddddddddd	|jd
|jd|jd|jd
|jd|jdg}t|d�D]\}}|j�d||�qP|j��dS)aaStandardize the excl arguments for the Httpd lens in Augeas.

        Note: Hack!
        Standardize the excl arguments for the Httpd lens in Augeas
        Servers sometimes give incorrect defaults
        Note: This problem should be fixed in Augeas 1.0.  Unfortunately,
        Augeas 0.10 appears to be the most popular version currently.

        z*.augnewz	*.augsavez*.dpkg-distz
*.dpkg-bakz
*.dpkg-newz
*.dpkg-oldz	*.rpmsavez*.rpmnewz*~z
/*.augsavez/*~z/*/*augsavez/*/*~z/*/*/*.augsavez/*/*/*~rqz/augeas/load/Httpd/excl[%d]N)rr�rrrL)r,ZexclrzZexcludedr.r.r/r"�s �
zApacheParser.standardize_exclcCsD|jd}tj�|jd�}tj�|�r0|}|}n|}|}|||d�S)z�Set default location for directives.

        Locations are given as file_paths
        .. todo:: Make sure that files are included

        rz
ports.conf)�default�listenr�)rrrrSr�isfile)r,r�Ztempr�r�r.r.r/r%�s
zApacheParser._set_locationscCsNdddg}|D]0}tj�tj�|j|��rtj�|j|�Sqt�d��dS)z(Find the Apache Configuration Root file.zapache2.confz
httpd.confzconf/httpd.confz!Could not find configuration rootN)rrr�rSrrr4)r,�locationr�r.r.r/r�s

zApacheParser._find_config_root)NrN)F)F)N)NNT)4�__name__�
__module__�__qualname__�__doc__r~rr�rr�r0rr=rrIrKrBrDr]r`rbr#r!rkrlrarsr}r�r�r�r�rXr�r�r�r*r�rir�r�r�r�r rxr�r�r�r�r�r"r%rr.r.r.r/rs`
�
6'
	


	

L5	 rcCsd�dd�t�|�D��S)a`Returns case insensitive regex.

    Returns a sloppy, but necessary version of a case insensitive regex.
    Any string should be able to be submitted and the string is
    escaped and then made case insensitive.
    May be replaced by a more proper /i once augeas 1.0 is widely
    supported.

    :param str string: string to make case i regex

    rAcSs0g|](}|��r(d|��|��dn|�qS)rr
)�isalpha�upperr�)rMrer.r.r/r��s�zcase_i.<locals>.<listcomp>)rSr~�escape)�stringr.r.r/rU�s
�rUcCsd|S)zTReturn augeas path for full filepath.

    :param str file_path: Full filepath

    z/files%sr.)Z	file_pathr.r.r/rW�srW)r�r&r�Zloggingr~r�r�rgZacme.magic_typingrrrZcertbotrZcertbot.compatrZcertbot_apacherZ	getLoggerr�rQ�objectrrUrWr.r.r.r/�<module>s,
N