Esempio n. 1
0
    def validate(self, section):
        if not isinstance(section, ConfigSection):
            raise ValidationError('Not a section')

        # Rebuild the section using schema:
        validated_section = ConfigSection(section.name, section.parent,
                                          position=section.position)
        # Validate the section's argument:
        if self.meta['args'] is None and section.args is not None:
            raise ValidationError('section %s, this section does not take '
                                  'any argument' % section.name,
                                  position=section.position)
        elif self.meta['args'] is not None:
            try:
                validated_args = self.meta['args'].validate(section.args_raw)
            except ValidationError as err:
                msg = 'section %s, arguments, %s' % (section.name, err)
                raise ValidationError(msg, position=err.position)
            else:
                validated_section.args = validated_args
        # Validate the section's children:
        for name, container in self.keys.items():
            if isinstance(container, Section):
                # Validate subsections of this section:
                subsections = list(section.subsections(name))
                # Check for repeat option:
                rmin, rmax = container.meta['repeat']
                if rmax is not None and rmin > rmax:
                    raise ValidationError('section %s, rmin > rmax' % name)
                if len(subsections) < rmin:
                    raise ValidationError('section %s, section must be defined'
                                          ' at least %d times' % (name, rmin))
                if rmax is not None and len(subsections) > rmax:
                    raise ValidationError('section %s, section must be defined'
                                          ' at max %d times' % (name, rmax))
                # Do the children validation:
                args = set()  # Store the already seen args
                for subsection in subsections:
                    # Check for unique option:
                    if container.meta['unique']:
                        args_value = None if subsection.args is None else tuple(subsection.args)
                        if args_value in args:
                            msg = 'section %s, section must be unique' % name
                            raise ValidationError(msg, position=subsection.position)
                        else:
                            args.add(args_value)
                    # Container validation:
                    validated_subsection = container.validate(subsection)
                    validated_section.register(validated_subsection, name=name)
            elif isinstance(container, Container):
                # Validate all other types of containers:
                try:
                    validated_value = container.validate(section.get(name, raw=False))
                except ValidationError as err:
                    raise ValidationError('section %s, key %s, %s' % (section.name, name, err),
                                          position=err.position)
                else:
                    validated_section.register(validated_value, name=name)
        # Handle the allow_unknown meta option:
        for name, child in section.iteritems():
            if name not in validated_section:
                if self.meta['allow_unknown']:
                    validated_section.register(child, name=name)
                else:
                    msg = 'section %s, unknown key %s' % (section.name, name)
                    raise ValidationError(msg, position=child.position)
        return validated_section