示例#1
0
    def validate(self, value):
        if value is None:
            return

        verrors = ValidationErrors()

        s = set()
        for i, v in enumerate(value):
            if self.unique:
                if isinstance(v, dict):
                    v = tuple(sorted(list(v.items())))
                if v in s:
                    verrors.add(f"{self.name}.{i}", "This value is not unique.")
                s.add(v)
            attr_verrors = ValidationErrors()
            for attr in self.items:
                try:
                    attr.validate(v)
                except ValidationErrors as e:
                    attr_verrors.add_child(f"{self.name}.{i}", e)
                else:
                    break
            else:
                verrors.extend(attr_verrors)

        if verrors:
            raise verrors

        super().validate(value)
示例#2
0
    def validate(self, value):
        verrors = ValidationErrors()

        if value:
            try:
                if self.cidr:
                    self.factory(value, strict=self.cidr_strict)
                else:
                    has_zone_index = False
                    if self.allow_zone_index and "%" in value:
                        has_zone_index = True
                        value = value[:value.rindex("%")]

                    addr = self.factory(value)

                    if has_zone_index and not isinstance(
                            addr, ipaddress.IPv6Address):
                        raise ValueError(
                            "Zone index is allowed only for IPv6 addresses")
            except ValueError as e:
                verrors.add(self.name, str(e), errno.EINVAL)

        if verrors:
            raise verrors

        return super().validate(value)
示例#3
0
    def validate(self, value):
        if value is None:
            return

        verrors = ValidationErrors()

        if value:
            try:
                if self.network:
                    self.factory(value, strict=self.network_strict)
                else:
                    if self.cidr and '/' not in value:
                        raise ValueError(
                            'Specified address should be in CIDR notation, e.g. 192.168.0.2/24'
                        )

                    has_zone_index = False
                    if self.allow_zone_index and "%" in value:
                        has_zone_index = True
                        value = value[:value.rindex("%")]

                    addr = self.factory(value)

                    if has_zone_index and not isinstance(
                            addr, ipaddress.IPv6Address):
                        raise ValueError(
                            "Zone index is allowed only for IPv6 addresses")
            except ValueError as e:
                verrors.add(self.name, str(e), errno.EINVAL)

        if verrors:
            raise verrors

        return super().validate(value)
示例#4
0
文件: jail.py 项目: DaveKuper/freenas
    def do_update(self, jail, options):
        """Sets a jail property."""
        plugin = options.pop("plugin")
        _, _, iocage = self.check_jail_existence(jail)

        name = options.pop("name", None)

        verrors = ValidationErrors()

        jail = self.query([['id', '=', jail]], {'get': True})

        verrors = self.common_validation(verrors, options, True, jail)

        if name is not None and plugin:
            verrors.add('options.plugin',
                        'Cannot be true while trying to rename')

        if verrors:
            raise verrors

        for prop, val in options.items():
            p = f"{prop}={val}"

            try:
                iocage.set(p, plugin)
            except RuntimeError as err:
                raise CallError(err)

        if name:
            iocage.rename(name)

        return True
示例#5
0
文件: schema.py 项目: freenas/freenas
    def validate(self, value):
        if value is None:
            return

        verrors = ValidationErrors()

        if value:
            try:
                if self.network:
                    self.factory(value, strict=self.network_strict)
                else:
                    if self.cidr and '/' not in value:
                        raise ValueError(
                            'Specified address should be in CIDR notation, e.g. 192.168.0.2/24'
                        )

                    has_zone_index = False
                    if self.allow_zone_index and "%" in value:
                        has_zone_index = True
                        value = value[:value.rindex("%")]

                    addr = self.factory(value)

                    if has_zone_index and not isinstance(addr, ipaddress.IPv6Address):
                        raise ValueError("Zone index is allowed only for IPv6 addresses")
            except ValueError as e:
                verrors.add(self.name, str(e), errno.EINVAL)

        if verrors:
            raise verrors

        return super().validate(value)
示例#6
0
def construct_schema(
    item_version_details: dict, new_values: dict, update: bool, old_values: Union[dict, object] = NOT_PROVIDED
) -> dict:
    schema_name = f'chart_release_{"update" if update else "create"}'
    attrs = list(itertools.chain.from_iterable(
        get_schema(q, update, old_values) for q in item_version_details['schema']['questions']
    ))
    dict_obj = update_conditional_defaults(
        Dict(schema_name, *attrs, update=update, additional_attrs=True), {
            'schema': {'attrs': item_version_details['schema']['questions']}
        }
    )

    verrors = ValidationErrors()
    verrors.add_child('values', validate_schema(
        attrs, new_values, True, dict_kwargs={
            'conditional_defaults': dict_obj.conditional_defaults, 'update': update,
        }
    ))
    return {
        'verrors': verrors,
        'new_values': new_values,
        'dict_obj': dict_obj,
        'schema_name': schema_name,
    }
示例#7
0
文件: jail.py 项目: DaveKuper/freenas
    def upgrade(self, job, jail, options):
        """Upgrades specified jail to specified RELEASE."""
        verrors = ValidationErrors()
        release = options.get('release', None)
        plugin = options['plugin']

        if release is None and not plugin:
            verrors.add(
                'options.release',
                'Must not be None if options.plugin is False.'
            )
            raise verrors

        job.set_progress(0, f'Upgrading {jail}')
        msg_queue = deque(maxlen=10)

        def progress_callback(content, exception):
            msg = content['message'].strip('\n')
            msg_queue.append(msg)
            final_msg = '\n'.join(msg_queue)

            if plugin:
                plugin_progress(job, msg)
            else:
                jail_progress(job, msg)

            job.set_progress(None, description=final_msg)

        def plugin_progress(job, msg):
            if 'Snapshotting' in msg:
                job.set_progress(20)
            elif 'Updating plugin INDEX' in msg:
                job.set_progress(40)
            elif 'Running upgrade' in msg:
                job.set_progress(70)
            elif 'Installing plugin packages' in msg:
                job.set_progress(90)
            elif f'{jail} successfully upgraded' in msg:
                job.set_progress(100)

        def jail_progress(job, msg):
            if 'Inspecting system' in msg:
                job.set_progress(20)
            elif 'Preparing to download files' in msg:
                job.set_progress(50)
            elif 'Applying patches' in msg:
                job.set_progress(75)
            elif 'Installing updates' in msg:
                job.set_progress(90)
            elif f'{jail} successfully upgraded' in msg:
                job.set_progress(100)

        _, _, iocage = self.check_jail_existence(
            jail,
            callback=progress_callback
        )
        iocage.upgrade(release=release)

        return True
示例#8
0
    def create_job(self, job, options):
        verrors = ValidationErrors()
        uuid = options["uuid"]

        job.set_progress(0, f'Creating: {uuid}')

        try:
            self.check_jail_existence(uuid, skip=False)

            verrors.add('uuid', f'A jail with name {uuid} already exists')
            raise verrors
        except CallError:
            # A jail does not exist with the provided name, we can create one
            # now

            verrors = self.common_validation(verrors, options)

            if verrors:
                raise verrors

            job.set_progress(20, 'Initial validation complete')

        iocage = ioc.IOCage(skip_jails=True)

        release = options["release"]
        template = options.get("template", False)
        pkglist = options.get("pkglist", None)
        basejail = options["basejail"]
        empty = options["empty"]
        short = options["short"]
        props = options["props"]
        pool = IOCJson().json_get_value("pool")
        iocroot = IOCJson(pool).json_get_value("iocroot")

        if template:
            release = template

        if (not os.path.isdir(f'{iocroot}/releases/{release}') and not template
                and not empty):
            job.set_progress(50, f'{release} missing, calling fetch')
            self.middleware.call_sync('jail.fetch', {"release": release},
                                      job=True)

        err, msg = iocage.create(release,
                                 props,
                                 0,
                                 pkglist,
                                 template=template,
                                 short=short,
                                 _uuid=uuid,
                                 basejail=basejail,
                                 empty=empty)

        if err:
            raise CallError(msg)

        job.set_progress(100, f'Created: {uuid}')

        return True
示例#9
0
文件: schema.py 项目: freenas/freenas
    def validate(self, value):
        verrors = ValidationErrors()

        for validator in self.validators:
            try:
                validator(value)
            except ValueError as e:
                verrors.add(self.name, str(e))

        if verrors:
            raise verrors
示例#10
0
    def validate(self, value):
        verrors = ValidationErrors()

        for validator in self.validators:
            try:
                validator(value)
            except ShouldBe as e:
                verrors.add(self.name, f"Should be {e.what}")

        if verrors:
            raise verrors
示例#11
0
    def validate(self, value):
        verrors = ValidationErrors()

        for validator in self.validators:
            try:
                validator(value)
            except ShouldBe as e:
                verrors.add(self.name, f"Should be {e.what}")

        if verrors:
            raise verrors
示例#12
0
    def validate(self, value):
        verrors = ValidationErrors()

        for validator in self.validators:
            try:
                validator(value)
            except ValueError as e:
                verrors.add(self.name, str(e))

        if verrors:
            raise verrors
示例#13
0
    def validate(self, value):
        verrors = ValidationErrors()

        for i, v in enumerate(value):
            for attr in self.items:
                try:
                    attr.validate(v)
                except ValidationErrors as e:
                    verrors.add_child(f"{self.name}.{i}", e)

        if verrors:
            raise verrors
示例#14
0
    def validate(self, value):
        verrors = ValidationErrors()

        for attr in self.attrs.values():
            if attr.name in value:
                try:
                    attr.validate(value[attr.name])
                except ValidationErrors as e:
                    verrors.add_child(self.name, e)

        if verrors:
            raise verrors
示例#15
0
    def validate(self, value):
        verrors = ValidationErrors()

        for i, v in enumerate(value):
            for attr in self.items:
                try:
                    attr.validate(v)
                except ValidationErrors as e:
                    verrors.add_child(f"{self.name}.{i}", e)

        if verrors:
            raise verrors
示例#16
0
    def validate(self, value):
        verrors = ValidationErrors()

        for attr in self.attrs.values():
            if attr.name in value:
                try:
                    attr.validate(value[attr.name])
                except ValidationErrors as e:
                    verrors.add_child(self.name, e)

        if verrors:
            raise verrors
示例#17
0
        def clean_and_validate_args(args, kwargs):
            args = list(args)
            args = args[:args_index] + copy.deepcopy(args[args_index:])
            kwargs = copy.deepcopy(kwargs)

            verrors = ValidationErrors()

            # Iterate over positional args first, excluding self
            i = 0
            for _ in args[args_index:]:
                attr = nf.accepts[i]

                value = attr.clean(args[args_index + i])
                args[args_index + i] = value

                try:
                    attr.validate(value)
                except ValidationErrors as e:
                    verrors.extend(e)

                i += 1

            # Use i counter to map keyword argument to rpc positional
            for x in list(range(i + 1, f.__code__.co_argcount)):
                kwarg = f.__code__.co_varnames[x]

                if kwarg in kwargs:
                    attr = nf.accepts[i]
                    i += 1

                    value = kwargs[kwarg]
                elif len(nf.accepts) >= i + args_index:
                    attr = nf.accepts[i]
                    i += 1

                    value = None
                else:
                    i += 1
                    continue

                value = attr.clean(value)
                kwargs[kwarg] = value

                try:
                    attr.validate(value)
                except ValidationErrors as e:
                    verrors.extend(e)

            if verrors:
                raise verrors

            return args, kwargs
示例#18
0
    def validate(self, value):
        verrors = ValidationErrors()

        if value:
            if not os.path.exists(value):
                verrors.add(self.name, "This path does not exist.", errno.ENOENT)
            elif not os.path.isfile(value):
                verrors.add(self.name, "This path is not a file.", errno.EISDIR)

        if verrors:
            raise verrors

        return super().validate(value)
示例#19
0
    def validate(self, value):
        verrors = ValidationErrors()

        for attr in self.attrs.values():
            if attr.name in value:
                try:
                    attr.validate(value[attr.name])
                except ValidationErrors as e:
                    verrors.add_child(self.name, e)

        for v in value:
            if v not in Cron.FIELDS:
                verrors.add(self.name, f'Unexpected {v} value')

        if verrors:
            raise verrors

        cron_expression = ''
        for field in Cron.FIELDS:
            cron_expression += value.get(field) + ' ' if value.get(
                field) else '* '

        try:
            croniter(cron_expression)
        except Exception as e:
            verrors.add(self.name,
                        'Please ensure fields match cron syntax - ' + str(e))

        if verrors:
            raise verrors
示例#20
0
def validate_return_type(func, result, schemas):
    if not schemas and result is None:
        return
    elif not schemas:
        raise ValueError(f'Return schema missing for {func.__name__!r}')

    result = copy.deepcopy(result)
    if not isinstance(result, tuple):
        result = [result]

    verrors = ValidationErrors()
    for res_entry, schema in zip(result, schemas):
        clean_and_validate_arg(verrors, schema, res_entry)
    verrors.check()
示例#21
0
    def validate(self, value):
        verrors = ValidationErrors()
        attr_verrors = ValidationErrors()
        for attr in self.schemas:
            try:
                attr.validate(value)
            except TypeError:
                pass
            except ValidationErrors as e:
                attr_verrors.extend(e)
            else:
                break
        else:
            verrors.extend(attr_verrors)

        verrors.check()
示例#22
0
    def do_update(self, jail, options):
        """Sets a jail property."""
        plugin = options.pop("plugin")
        _, _, iocage = self.check_jail_existence(jail)

        name = options.pop("name", None)

        verrors = ValidationErrors()

        jail = self.query([['id', '=', jail]], {'get': True})

        exclude_ips = [
            ip.split('|')[1].split('/')[0] if '|' in ip else ip.split('/')[0]
            for f in ('ip4_addr', 'ip6_addr') for ip in jail[f].split(',')
            if ip != 'none'
        ]

        self.validate_ips(
            verrors, {'props': [f'{k}={v}' for k, v in options.items()]},
            'options', exclude_ips
        )

        for prop, val in options.items():
            p = f"{prop}={val}"

            try:
                iocage.set(p, plugin)
            except RuntimeError as err:
                raise CallError(err)

        if name:
            iocage.rename(name)

        return True
示例#23
0
文件: schema.py 项目: freenas/freenas
    def validate(self, value):
        if value is None:
            return

        verrors = ValidationErrors()

        if value:
            if not os.path.exists(value):
                verrors.add(self.name, "This path does not exist.", errno.ENOENT)
            elif not os.path.isdir(value):
                verrors.add(self.name, "This path is not a directory.", errno.ENOTDIR)

        if verrors:
            raise verrors

        return super().validate(value)
示例#24
0
    def validate(self, value):
        verrors = ValidationErrors()

        for attr in self.attrs.values():
            if attr.name in value:
                try:
                    attr.validate(value[attr.name])
                except ValidationErrors as e:
                    verrors.add_child(self.name, e)

        for v in value:
            if v not in Cron.FIELDS:
                verrors.add(self.name, f'Unexpected {v} value')

        if verrors:
            raise verrors

        cron_expression = ''
        for field in Cron.FIELDS:
            cron_expression += value.get(field) + ' ' if value.get(field) else '* '

        try:
            croniter(cron_expression)
        except Exception as e:
            verrors.add(self.name, 'Please ensure fields match cron syntax - ' + str(e))

        if verrors:
            raise verrors
示例#25
0
    def get_attrs_to_skip(self, data):
        skip_attrs = defaultdict(set)
        check_data = self.get_defaults(data, {}, ValidationErrors(), False) if not self.update else data
        for attr, attr_data in filter(
            lambda k: not filter_list([check_data], k[1]['filters']), self.conditional_defaults.items()
        ):
            for k in attr_data['attrs']:
                skip_attrs[k].update({attr})

        return skip_attrs
示例#26
0
        def clean_and_validate_args(args, kwargs):
            args = list(args)

            common_args = args[:args_index]
            signature_args = args[args_index:]

            had_warning = False
            for check, adapt in deprecated:
                if check(signature_args):
                    if not had_warning:
                        warnings.warn(
                            f"Method {f!r} was called with a deprecated signature",
                            DeprecationWarning)
                        had_warning = True
                    signature_args = adapt(*signature_args)

            args = common_args + copy.deepcopy(signature_args)
            kwargs = copy.deepcopy(kwargs)

            verrors = ValidationErrors()

            # Iterate over positional args first, excluding self
            i = 0
            if len(args[args_index:]) > len(nf.accepts):
                raise CallError(
                    f'Too many arguments (expected {len(nf.accepts)}, found {len(args[args_index:])})'
                )
            for _ in args[args_index:]:
                args[args_index + i] = clean_and_validate_arg(
                    verrors, nf.accepts[i], args[args_index + i])
                i += 1

            # Use i counter to map keyword argument to rpc positional
            for x in list(range(i + args_index, f.__code__.co_argcount)):
                kwarg = f.__code__.co_varnames[x]

                if kwarg in kwargs:
                    attr = nf.accepts[i]
                    i += 1

                    value = kwargs[kwarg]
                elif len(nf.accepts) >= i + 1:
                    attr = nf.accepts[i]
                    i += 1
                    value = NOT_PROVIDED
                else:
                    i += 1
                    continue

                kwargs[kwarg] = clean_and_validate_arg(verrors, attr, value)

            if verrors:
                raise verrors

            return args, kwargs
示例#27
0
    def fetch(self, job, options):
        """Fetches a release or plugin."""
        fetch_output = {'error': False, 'install_notes': []}

        verrors = ValidationErrors()

        self.validate_ips(verrors, options)

        def progress_callback(content):
            level = content['level']
            msg = content['message'].strip('\n')

            if job.progress['percent'] == 90:
                for split_msg in msg.split('\n'):
                    fetch_output['install_notes'].append(split_msg)

            if level == 'EXCEPTION':
                fetch_output['error'] = True
                raise CallError(msg)

            job.set_progress(None, msg)

            if '  These pkgs will be installed:' in msg:
                job.set_progress(50, msg)
            elif 'Installing plugin packages:' in msg:
                job.set_progress(75, msg)
            elif 'Command output:' in msg:
                job.set_progress(90, msg)

        self.check_dataset_existence()  # Make sure our datasets exist.
        start_msg = None
        finaL_msg = None

        if options["name"] is not None:
            options["plugin_file"] = True
            start_msg = 'Starting plugin install'
            finaL_msg = f"Plugin: {options['name']} installed"

        options["accept"] = True

        iocage = ioc.IOCage(callback=progress_callback, silent=False)

        job.set_progress(0, start_msg)
        iocage.fetch(**options)

        if options['name'] is not None:
            # This is to get the admin URL and such
            fetch_output['install_notes'] += job.progress['description'].split(
                '\n')

        job.set_progress(100, finaL_msg)

        return fetch_output
示例#28
0
 def validate(self, value):
     super().validate(value)
     verrors = ValidationErrors()
     uri = urlparse(value)
     if not all(getattr(uri, k) for k in ('scheme', 'netloc')):
         verrors.add(self.name, 'Not a valid URI')
     verrors.check()
示例#29
0
    def validate(self, value):
        if value is None:
            return

        verrors = ValidationErrors()

        for attr in self.attrs.values():
            if attr.name in value:
                try:
                    attr.validate(value[attr.name])
                except ValidationErrors as e:
                    verrors.add_child(self.name, e)

        for v in value:
            if self.begin_end and v in ['begin', 'end']:
                continue
            if v not in Cron.FIELDS:
                verrors.add(self.name, f'Unexpected {v} value')

        if verrors:
            raise verrors

        cron_expression = ''
        for field in Cron.FIELDS:
            cron_expression += value.get(field) + ' ' if value.get(
                field) else '* '

        try:
            croniter(cron_expression)
        except Exception as e:
            verrors.add(self.name,
                        'Please ensure fields match cron syntax - ' + str(e))

        if value.get('begin') and value.get('end') and not (
                value.get('begin') <= value.get('end')):
            verrors.add(self.name,
                        'Begin time should be less or equal than end time')

        if verrors:
            raise verrors
示例#30
0
    def clean(self, data):
        data = super().clean(data)

        if data is None:
            if self.null:
                return None

            return copy.deepcopy(self.default)

        if not isinstance(data, dict):
            raise Error(self.name, 'A dict was expected')

        verrors = ValidationErrors()
        for key, value in list(data.items()):
            if not self.additional_attrs:
                if key not in self.attrs:
                    verrors.add(f'{self.name}.{key}', 'Field was not expected')
                    continue

            attr = self.attrs.get(key)
            if not attr:
                continue

            data[key] = self._clean_attr(attr, value, verrors)

        # Do not make any field and required and not populate default values
        if not self.update:
            data.update(self.get_defaults(data, self.get_attrs_to_skip(data), verrors))

        verrors.check()

        return data
示例#31
0
    def _do_create(self, job, data):
        self.middleware.call_sync('jail.check_dataset_existence')
        verrors = ValidationErrors()
        branch = data.pop('branch') or self.get_version()
        install_notes = ''
        plugin_name = data.pop('plugin_name')
        jail_name = data.pop('jail_name')
        plugin_repository = data.pop('plugin_repository')
        post_install = False

        job.set_progress(0, f'Creating plugin: {plugin_name}')
        if jail_name in [
                j['id'] for j in self.middleware.call_sync('jail.query')
        ]:
            verrors.add('plugin_create.jail_name',
                        f'A jail with name {jail_name} already exists')
        else:
            verrors = common_validation(self.middleware,
                                        data,
                                        schema='plugin_create')

        verrors.check()

        job.set_progress(20, 'Initial validation complete')

        def progress_callback(content, exception):
            msg = content['message'].strip('\r\n')
            nonlocal install_notes, post_install

            if post_install and msg:
                install_notes += f'\n{msg}'

            if '  These pkgs will be installed:' in msg:
                job.set_progress(50, msg)
            elif 'Installing plugin packages:' in msg:
                job.set_progress(75, msg)
            elif 'Running post_install.sh' in msg:
                job.set_progress(90, msg)
                # Sets each message going forward as important to the user
                post_install = True
            else:
                job.set_progress(None, msg)

        ioc.IOCage(callback=progress_callback, silent=False).fetch(
            **{
                'accept': True,
                'name': jail_name,
                'plugin_name': plugin_name,
                'git_repository': plugin_repository,
                'props': data['props'],
                'branch': branch,
            })

        new_plugin = self.middleware.call_sync('plugin._get_instance',
                                               jail_name)
        new_plugin['install_notes'] = install_notes.strip()

        return new_plugin
示例#32
0
    def clone(self, job, source_jail, options):
        verrors = ValidationErrors()
        try:
            self.check_jail_existence(source_jail, skip=False)
        except CallError:
            verrors.add('source_jail', f'{source_jail} does not exist.',
                        errno.ENOENT)
        else:
            try:
                self.check_jail_existence(options['uuid'], skip=False)
            except CallError:
                pass
            else:
                verrors.add(
                    'clone_jail.uuid',
                    f'Jail with "{options["uuid"]}" uuid already exists.',
                    errno.EEXIST)

        verrors.check()
        verrors = common_validation(self.middleware,
                                    options,
                                    schema='clone_jail')
        verrors.check()

        job.set_progress(25, 'Initial validation complete.')

        ioc.IOCage(jail=source_jail,
                   skip_jails=True).create(source_jail,
                                           options['props'],
                                           _uuid=options['uuid'],
                                           thickjail=options['thickjail'],
                                           clone=True)

        job.set_progress(100, 'Jail has been successfully cloned.')

        return self.middleware.call_sync('jail._get_instance', options['uuid'])
示例#33
0
    def validate(self, value):
        verrors = ValidationErrors()

        if value:
            try:
                if self.cidr:
                    self.factory(value, strict=self.cidr_strict)
                else:
                    has_zone_index = False
                    if self.allow_zone_index and "%" in value:
                        has_zone_index = True
                        value = value[:value.rindex("%")]

                    addr = self.factory(value)

                    if has_zone_index and not isinstance(addr, ipaddress.IPv6Address):
                        raise ValueError("Zone index is allowed only for IPv6 addresses")
            except ValueError as e:
                verrors.add(self.name, str(e), errno.EINVAL)

        if verrors:
            raise verrors

        return super().validate(value)
示例#34
0
文件: schema.py 项目: freenas/freenas
    def validate(self, value):
        if value is None:
            return

        verrors = ValidationErrors()

        s = set()
        for i, v in enumerate(value):
            if self.unique:
                if isinstance(v, dict):
                    v = tuple(sorted(list(v.items())))
                if v in s:
                    verrors.add(f"{self.name}.{i}", "This value is not unique.")
                s.add(v)
            for attr in self.items:
                try:
                    attr.validate(v)
                except ValidationErrors as e:
                    verrors.add_child(f"{self.name}.{i}", e)

        if verrors:
            raise verrors

        super().validate(value)
示例#35
0
        def clean_and_validate_args(args, kwargs):
            args = list(args)
            args = args[:args_index] + copy.deepcopy(args[args_index:])
            kwargs = copy.deepcopy(kwargs)

            verrors = ValidationErrors()

            def clean_and_validate_arg(attr, arg):
                try:
                    value = attr.clean(arg)
                    attr.validate(value)
                    return value
                except Error as e:
                    verrors.add(e.attribute, e.errmsg, e.errno)
                except ValidationErrors as e:
                    verrors.extend(e)

            # Iterate over positional args first, excluding self
            i = 0
            for _ in args[args_index:]:
                args[args_index + i] = clean_and_validate_arg(
                    nf.accepts[i], args[args_index + i])
                i += 1

            # Use i counter to map keyword argument to rpc positional
            for x in list(range(i + args_index, f.__code__.co_argcount)):
                kwarg = f.__code__.co_varnames[x]

                if kwarg in kwargs:
                    attr = nf.accepts[i]
                    i += 1

                    value = kwargs[kwarg]
                elif len(nf.accepts) >= i + 1:
                    attr = nf.accepts[i]
                    i += 1
                    value = NOT_PROVIDED
                else:
                    i += 1
                    continue

                kwargs[kwarg] = clean_and_validate_arg(attr, value)

            if verrors:
                raise verrors

            return args, kwargs
示例#36
0
    def validate(self, value):
        if value is None:
            return

        verrors = ValidationErrors()

        if not dn.is_dn(value):
            verrors.add(self.name, "Invalid LDAP DN specified.")

        verrors.check()
        return super().validate(value)
示例#37
0
    async def check_disks_availability(self, disks, allow_duplicate_serials):
        """
        Makes sure the disks are present in the system and not reserved
        by anything else (boot, pool, iscsi, etc).

        Returns:
            verrors, dict - validation errors (if any) and disk.query for all disks
        """
        verrors = ValidationErrors()
        disks_cache = dict(map(lambda x: (x['devname'], x), await self.middleware.call('disk.query')))

        disks_set = set(disks)
        disks_not_in_cache = disks_set - set(disks_cache.keys())
        if disks_not_in_cache:
            verrors.add(
                'topology',
                f'The following disks were not found in system: {"," .join(disks_not_in_cache)}.'
            )

        disks_reserved = await self.middleware.call('disk.get_reserved')
        already_used = disks_set - (disks_set - set(disks_reserved))
        if already_used:
            verrors.add(
                'topology',
                f'The following disks are already in use: {"," .join(already_used)}.'
            )

        if not allow_duplicate_serials and not verrors:
            serial_to_disk = defaultdict(set)
            for disk in disks:
                serial_to_disk[(disks_cache[disk]['serial'], disks_cache[disk]['lunid'])].add(disk)
            for reserved_disk in disks_reserved:
                reserved_disk_cache = disks_cache.get(reserved_disk)
                if not reserved_disk_cache:
                    continue

                serial_to_disk[(reserved_disk_cache['serial'], reserved_disk_cache['lunid'])].add(reserved_disk)

            if duplicate_serials := {serial for serial, serial_disks in serial_to_disk.items()
                                     if len(serial_disks) > 1}:
                error = ', '.join(map(lambda serial: f'{serial[0]!r} ({", ".join(sorted(serial_to_disk[serial]))})',
                                      duplicate_serials))
                verrors.add('topology', f'Disks have duplicate serial numbers: {error}.')
示例#38
0
    def validate(self, value):
        if value is None:
            return value

        verrors = ValidationErrors()

        if value and len(str(value)) > self.max_length:
            verrors.add(self.name, f'Value greater than {self.max_length} not allowed')

        verrors.check()

        return super().validate(value)
示例#39
0
        def clean_and_validate_args(args, kwargs):
            args = list(args)
            args = args[:args_index] + copy.deepcopy(args[args_index:])
            kwargs = copy.deepcopy(kwargs)

            verrors = ValidationErrors()

            # Iterate over positional args first, excluding self
            i = 0
            for _ in args[args_index:]:
                attr = nf.accepts[i]

                value = attr.clean(args[args_index + i])
                args[args_index + i] = value

                try:
                    attr.validate(value)
                except ValidationErrors as e:
                    verrors.extend(e)

                i += 1

            # Use i counter to map keyword argument to rpc positional
            for x in list(range(i + 1, f.__code__.co_argcount)):
                kwarg = f.__code__.co_varnames[x]

                if kwarg in kwargs:
                    attr = nf.accepts[i]
                    i += 1

                    value = kwargs[kwarg]
                elif len(nf.accepts) >= i + args_index:
                    attr = nf.accepts[i]
                    i += 1

                    value = None
                else:
                    i += 1
                    continue

                value = attr.clean(value)
                kwargs[kwarg] = value

                try:
                    attr.validate(value)
                except ValidationErrors as e:
                    verrors.extend(e)

            if verrors:
                raise verrors

            return args, kwargs
示例#40
0
    def validate(self, value):
        verrors = ValidationErrors()

        if value:
            if not os.path.exists(value):
                verrors.add(self.name, "This path does not exist.", errno.ENOENT)
            elif not os.path.isfile(value):
                verrors.add(self.name, "This path is not a file.", errno.EISDIR)

        if verrors:
            raise verrors

        return super().validate(value)
示例#41
0
 async def validate(self, data, dev):
     verrors = ValidationErrors()
     unavail = [
         i for i in data['capabilities']
         if i not in dev.supported_capabilities
     ]
     if unavail:
         # gave us a capability that isn't supported on the device
         # or is "fixed" (meaning it can't be changed)
         verrors.add(
             f'capabilities_set.{data["action"]}',
             f'"{data["name"]}" does not support "{", ".join(unavail)}"')
     verrors.check()
示例#42
0
文件: schema.py 项目: freenas/freenas
    def validate(self, value):
        if value is None:
            return

        verrors = ValidationErrors()

        for attr in self.attrs.values():
            if attr.name in value:
                try:
                    attr.validate(value[attr.name])
                except ValidationErrors as e:
                    verrors.add_child(self.name, e)

        for v in value:
            if self.begin_end and v in ['begin', 'end']:
                continue
            if v not in Cron.FIELDS:
                verrors.add(self.name, f'Unexpected {v} value')

        if verrors:
            raise verrors

        cron_expression = ''
        for field in Cron.FIELDS:
            cron_expression += value.get(field) + ' ' if value.get(field) else '* '

        try:
            croniter(cron_expression)
        except Exception as e:
            verrors.add(self.name, 'Please ensure fields match cron syntax - ' + str(e))

        if value.get('begin') and value.get('end') and not (value.get('begin') <= value.get('end')):
            verrors.add(self.name, 'Begin time should be less or equal than end time')

        if verrors:
            raise verrors