Exemple #1
0
    def set_options(self):
        if self.vars.options is None:
            return

        actionable_snaps = [s for s in self.vars.name if self.is_snap_installed(s)]
        overall_options_changed = []

        for snap_name in actionable_snaps:
            option_map = self.retrieve_option_map(snap_name=snap_name)

            options_changed = []

            for option_string in self.vars.options:
                match = self.__set_param_re.match(option_string)

                if not match:
                    msg = "Cannot parse set option '{option_string}'".format(option_string=option_string)
                    raise ModuleHelperException(msg)

                snap_prefix = match.group("snap_prefix")
                selected_snap_name = snap_prefix[:-1] if snap_prefix else None

                if selected_snap_name is not None and selected_snap_name not in self.vars.name:
                    msg = "Snap option '{option_string}' refers to snap which is not in the list of snap names".format(option_string=option_string)
                    raise ModuleHelperException(msg)

                if selected_snap_name is None or (snap_name is not None and snap_name == selected_snap_name):
                    key = match.group("key")
                    value = match.group("value")

                    if key not in option_map or key in option_map and option_map[key] != value:
                        option_without_prefix = key + "=" + value
                        option_with_prefix = option_string if selected_snap_name is not None else snap_name + ":" + option_string
                        options_changed.append(option_without_prefix)
                        overall_options_changed.append(option_with_prefix)

            if options_changed:
                self.changed = True

                if not self.module.check_mode:
                    params = [{'state': 'set'}, {'name': snap_name}, {'options': options_changed}]

                    rc, out, err = self.run_command(params=params)

                    if rc != 0:
                        if 'has no "configure" hook' in err:
                            msg = "Snap '{snap}' does not have any configurable options".format(snap=snap_name)
                            raise ModuleHelperException(msg)

                        msg = "Cannot set options '{options}' for snap '{snap}': error={error}".format(
                            options=" ".join(options_changed), snap=snap_name, error=err)
                        raise ModuleHelperException(msg)

        if overall_options_changed:
            self.vars.options_changed = overall_options_changed
Exemple #2
0
    def __init_module__(self):
        v = self.vars
        if v.mode == "compatibility":
            if v.name_check:
                raise ModuleHelperException("Parameter name_check can only be used with mode=new")
        else:
            if v.name and v.from_path:
                raise ModuleHelperException("Parameters 'name' and 'from_path' are mutually exclusive when 'mode=new'")
            if v.system_lib:
                raise ModuleHelperException("Parameter 'system_lib' is invalid when 'mode=new'")

        self.command = self.module.get_bin_path(v.executable if v.executable else self.command)
        self.vars.set("binary", self.command)
Exemple #3
0
 def sanitize_pkg_spec_version(pkg_spec, version):
     if version is None:
         return pkg_spec
     if pkg_spec.endswith('.tar.gz'):
         raise ModuleHelperException(msg="parameter 'version' must not be used when installing from a file")
     if os.path.isdir(pkg_spec):
         raise ModuleHelperException(msg="parameter 'version' must not be used when installing from a directory")
     if pkg_spec.endswith('.git'):
         if version.startswith('~'):
             raise ModuleHelperException(msg="operator '~' not allowed in version parameter when installing from git repository")
         version = version if version.startswith('@') else '@' + version
     elif version[0] not in ('@', '~'):
         version = '~' + version
     return pkg_spec + version
Exemple #4
0
 def state_reinstall(self):
     if not self.vars.application:
         raise ModuleHelperException(
             "Trying to reinstall a non-existent application: {0}".format(self.vars.name))
     self.changed = True
     if not self.module.check_mode:
         self.run_command(params=['state', 'name', 'python'])
Exemple #5
0
    def state_present(self):
        self.vars.meta('classic').set(output=True)
        self.vars.meta('channel').set(output=True)
        actionable_snaps = [s for s in self.vars.name if not self.is_snap_installed(s)]
        if not actionable_snaps:
            return
        self.changed = True
        self.vars.snaps_installed = actionable_snaps
        if self.module.check_mode:
            return
        params = ['state', 'classic', 'channel']  # get base cmd parts
        has_one_pkg_params = bool(self.vars.classic) or self.vars.channel != 'stable'
        has_multiple_snaps = len(actionable_snaps) > 1
        if has_one_pkg_params and has_multiple_snaps:
            commands = [params + [{'actionable_snaps': [s]}] for s in actionable_snaps]
        else:
            commands = [params + [{'actionable_snaps': actionable_snaps}]]
        self.vars.cmd, rc, out, err = self._run_multiple_commands(commands)
        if rc == 0:
            return

        classic_snap_pattern = re.compile(r'^error: This revision of snap "(?P<package_name>\w+)"'
                                          r' was published using classic confinement')
        match = classic_snap_pattern.match(err)
        if match:
            err_pkg = match.group('package_name')
            msg = "Couldn't install {name} because it requires classic confinement".format(name=err_pkg)
        else:
            msg = "Ooops! Snap installation failed while executing '{cmd}', please examine logs and " \
                  "error output for more details.".format(cmd=self.vars.cmd)
        raise ModuleHelperException(msg=msg)
Exemple #6
0
 def state_inject(self):
     if not self.vars.application:
         raise ModuleHelperException(
             "Trying to inject packages into a non-existent application: {0}".format(self.vars.name))
     if self.vars.force:
         self.changed = True
     if not self.module.check_mode:
         self.run_command(params=['state', 'index_url', 'force', 'name', 'inject_packages'])
Exemple #7
0
 def state_upgrade(self):
     if not self.vars.application:
         raise ModuleHelperException(
             "Trying to upgrade a non-existent application: {0}".format(self.vars.name))
     if self.vars.force:
         self.changed = True
     if not self.module.check_mode:
         self.run_command(params=['state', 'index_url', 'install_deps', 'force', 'name'])
Exemple #8
0
    def __init_module__(self):
        self.does_not = 'Property "{0}" does not exist on channel "{1}".'.format(self.module.params['property'],
                                                                                 self.module.params['channel'])
        self.vars.set('previous_value', self._get(), fact=True)
        self.vars.set('type', self.vars.value_type, fact=True)
        self.vars.meta('value').set(initial_value=self.vars.previous_value)

        if self.module.params['disable_facts'] is False:
            raise ModuleHelperException('Returning results as facts has been removed. Stop using disable_facts=false.')
Exemple #9
0
 def is_snap_enabled(self, snap_name):
     rc, out, err = self.run_command(params=[{'state': 'list'}, {'name': snap_name}])
     if rc != 0:
         return None
     result = out.splitlines()[1]
     match = self.__disable_re.match(result)
     if not match:
         raise ModuleHelperException(msg="Unable to parse 'snap list {0}' output:\n{1}".format(snap_name, out))
     notes = match.group('notes')
     return "disabled" not in notes.split(',')
Exemple #10
0
 def _generic_state_action(self, actionable_func, actionable_var, params=None):
     actionable_snaps = [s for s in self.vars.name if actionable_func(s)]
     if not actionable_snaps:
         return
     self.changed = True
     self.vars[actionable_var] = actionable_snaps
     if self.module.check_mode:
         return
     if params is None:
         params = ['state']
     commands = [params + [{'actionable_snaps': actionable_snaps}]]
     self.vars.cmd, rc, out, err = self._run_multiple_commands(commands)
     if rc == 0:
         return
     msg = "Ooops! Snap operation failed while executing '{cmd}', please examine logs and " \
           "error output for more details.".format(cmd=self.vars.cmd)
     raise ModuleHelperException(msg=msg)
Exemple #11
0
    def convert_json_subtree_to_map(self, json_subtree, prefix=None):
        option_map = {}

        if not isinstance(json_subtree, dict):
            raise ModuleHelperException("Non-dict non-leaf element encountered while parsing option map. "
                                        "The output format of 'snap set' may have changed. Aborting!")

        for key, value in json_subtree.items():
            full_key = key if prefix is None else prefix + "." + key

            if isinstance(value, (str, float, bool, numbers.Integral)):
                option_map[full_key] = str(value)

            else:
                option_map.update(self.convert_json_subtree_to_map(json_subtree=value, prefix=full_key))

        return option_map
Exemple #12
0
 def state_disabled(self):
     self.validate_input_snaps()
     actionable_snaps = [s for s in self.vars.name if self.is_snap_enabled(s) is True]
     if not actionable_snaps:
         return
     self.changed = True
     self.vars.snaps_enabled = actionable_snaps
     if self.module.check_mode:
         return
     params = ['classic', 'channel', 'state']  # get base cmd parts
     commands = [params + actionable_snaps]
     self.vars.cmd, rc, out, err = self._run_multiple_commands(commands)
     if rc == 0:
         return
     msg = "Ooops! Snap disabling failed while executing '{cmd}', please examine logs and " \
           "error output for more details.".format(cmd=self.vars.cmd)
     raise ModuleHelperException(msg=msg)
Exemple #13
0
 def state_absent(self):
     self.validate_input_snaps(
     )  # if snap doesnt exist, it will be absent by definition
     actionable_snaps = [
         s for s in self.vars.name if self.is_snap_installed(s)
     ]
     if not actionable_snaps:
         return
     self.changed = True
     self.vars.snaps_removed = actionable_snaps
     if self.module.check_mode:
         return
     params = ['classic', 'channel', 'state']  # get base cmd parts
     commands = [params + [{'actionable_snaps': actionable_snaps}]]
     self.vars.cmd, rc, out, err = self._run_multiple_commands(commands)
     if rc == 0:
         return
     msg = "Ooops! Snap removal failed while executing '{cmd}', please examine logs and " \
           "error output for more details.".format(cmd=self.vars.cmd)
     raise ModuleHelperException(msg=msg)
Exemple #14
0
    def retrieve_option_map(self, snap_name):
        params = [{'state': 'get'}, {'name': snap_name}, {'json_format': True}]
        rc, out, err = self.run_command(params=params)

        if rc != 0:
            return {}

        result = out.splitlines()

        if "has no configuration" in result[0]:
            return {}

        try:
            option_map = self.convert_json_to_map(out)

        except Exception as e:
            raise ModuleHelperException(
                msg="Parsing option map returned by 'snap get {0}' triggers exception '{1}', output:\n'{2}'".format(snap_name, str(e), out))

        return option_map
Exemple #15
0
 def process_command_output(self, rc, out, err):
     if rc != 0:
         raise ModuleHelperException("mksysb failed.")
     self.vars.msg = out
Exemple #16
0
 def process_command_output(self, rc, out, err):
     if self.vars.mode == "compatibility" and rc != 0:
         raise ModuleHelperException(msg=err, cmd=self.vars.cmd_args)
     return 'is up to date' not in err and 'is up to date' not in out
Exemple #17
0
 def validate_input_snaps(self):
     """Ensure that all exist."""
     for snap_name in self.vars.name:
         if not self.snap_exists(snap_name):
             raise ModuleHelperException(
                 msg="No snap matching '%s' available." % snap_name)
Exemple #18
0
 def __init_module__(self):
     if not os.path.isdir(self.vars.storage_path):
         raise ModuleHelperException("Storage path %s is not valid." %
                                     self.vars.storage_path)