예제 #1
0
    def validate(self, value: str | None, path: list[str],
                 **kwargs: Any) -> str | None:
        """
        Currently only validates by running urlparse against it
        and checking that a scheme and netloc is set - and if a list of allowed
        schemes is provide that the scheme is valid against that list

        TODO: may want something more sophisticated than that - could look
        at django's url validator
        """
        value = super().validate(value, path, **kwargs)

        if value == "" and self.blank:
            return value

        if value is None and self.default_is_none:
            return value

        try:
            result = urlparse(value)
        except ValueError:
            raise ValidationError(self, path, value, "url expected")

        if not result.scheme:
            raise ValidationError(self, path, value, "no url scheme specified")

        if not result.netloc:
            raise ValidationError(self, path, value, "no url netloc specified")

        if self.schemes and result.scheme not in self.schemes:
            raise ValidationError(self, path, value,
                                  f"invalid url scheme: {result.scheme}")

        return value
예제 #2
0
파일: core.py 프로젝트: 20c/confu
    def validate(self, value: Any, path: list[str], **kwargs: Any) -> Any:
        """
        Validate a value for this attribute

        Will raise a `ValidationError` or `ValidationWarning` exception on
        validation failure

        **Arguments**

        - value (`mixed`): the value to validate
        - path (`list`): current path in the config schema, this is mostly
          used to identify where an error occured when validating
          against config data, you can pass an empty list to it when
          calling this manually
        """

        if not self.container and not self.name:
            raise ValidationError(
                self, path, value,
                "attribute at top level defined without a name")

        if self.choices_handler:
            if value not in self.choices:
                raise ValidationError(self, path, value, "invalid choice")
        return value
예제 #3
0
파일: core.py 프로젝트: roysc/confu
    def validate(self, config, path=None, errors=None, warnings=None):
        """
        Validate config data against this schema

        **Attributes**

        - config (`dict`): config to validate

        **Keyword Attributes**

        - path (`list`): current path in the config data, this can be
          ignored on the initial call and will be set automatically
          on any subsequent calls (nested schemas)
        - errors (`ValidationErrorProcessor`)
        - warnigns (`ValidationErrorProcessor`)
        """

        if path is None:
            path = []
        if errors is None:
            errors = ValidationErrorProcessor()
        if warnings is None:
            warnings = ValidationErrorProcessor()

        # munge Config support without having to import munge
        if isinstance(config, collections.MutableMapping) and hasattr(
                config, "data"):
            config = config.data
        elif isinstance(config, configparser.ConfigParser):
            config = config_parser_dict(config)

        if not isinstance(config, dict):
            return errors.error(
                ValidationError(path[-1], path, config, "dictionary expected"))

        for key, value in config.items():
            try:
                attribute = self._attr.get(key, self.item)

                if attribute is None:
                    raise ValidationWarning(
                        key, path, value, "unknown attribute '{}'".format(key))
                else:
                    config[key] = attribute.validate(value,
                                                     path + [key],
                                                     errors=errors,
                                                     warnings=warnings)
            except ValidationError as error:
                errors.error(error)
            except ValidationWarning as warning:
                warnings.warning(warning)

        for name, attribute in self.attributes():
            if name not in config and not attribute.has_default:
                errors.error(
                    ValidationError(attribute, path + [name], None, "missing"))

        return config
예제 #4
0
파일: core.py 프로젝트: roysc/confu
    def validate(self, value, path, **kwargs):
        if not isinstance(value,
                          six.string_types) and not self.default_is_none:
            raise ValidationError(self, path, value, "string expected")

        if value == "" and not self.blank:
            raise ValidationError(self, path, value, "cannot be blank")

        return super(Str, self).validate(value, path, **kwargs)
예제 #5
0
파일: core.py 프로젝트: 20c/confu
    def validate(
        self,
        value: str | None,
        path: list[str],
        **kwargs: Any,
    ) -> str | None:
        if not isinstance(value, str) and not self.default_is_none:
            raise ValidationError(self, path, value, "string expected")

        if value == "" and not self.blank:
            raise ValidationError(self, path, value, "cannot be blank")

        return super().validate(value, path, **kwargs)
예제 #6
0
파일: core.py 프로젝트: 20c/confu
    def validate(
        self,
        value: list | str,
        path: list[str],
        **kwargs: Any,
    ) -> Any:

        if isinstance(value, str):
            value = value.split(",")

        if not isinstance(value, list):
            raise ValidationError(self, path, value, "list expected")

        errors = kwargs.get("errors", ValidationErrorProcessor())
        warnings = kwargs.get("warnings", ValidationErrorProcessor())

        validated = []
        idx = 0
        for item in value:
            try:
                if isinstance(self.item, Schema):
                    validated.append(
                        self.item.validate(item,
                                           path + [idx],
                                           errors=errors,
                                           warnings=warnings))
                else:
                    validated.append(self.item.validate(item, path + [idx]))
                idx += 1
            except ValidationError as error:
                errors.error(error)
            except ValidationWarning as warning:
                warnings.warning(warning)
        return super().validate(validated, path, **kwargs)
예제 #7
0
파일: core.py 프로젝트: roysc/confu
    def validate(self, value, path, **kwargs):
        value = super(Directory, self).validate(value, path, **kwargs)

        if value is None and self.default_is_none:
            return value

        # make sure env vars get expanded
        value = os.path.expandvars(value)

        # if value is blank, and validation was not caught by `blank` validation
        # of Str we forfeit validation and it is assume that the application
        # will validate manually once the path is set.
        if value == "":
            return value

        # make sure user vars get expanded
        value = os.path.expanduser(value)

        # expand to absolute path
        value = os.path.abspath(value)

        if self.create is not None and not os.path.exists(value):
            self.makedir(value, path)

        if self.require_exist:
            valid = os.path.exists(value) and os.path.isdir(value)
        else:
            valid = True

        if not valid:
            raise ValidationError(
                self, path, value,
                "valid path to directory expected: {}".format(value))

        return value
예제 #8
0
파일: core.py 프로젝트: 20c/confu
    def validate(self, value: str | None, path: list[str],
                 **kwargs: Any) -> str | None:
        value = super().validate(value, path, **kwargs)

        if value is None and self.default_is_none:
            return value

        if value == "" and self.blank:
            return value

        # make sure env vars get expanded
        value = os.path.expandvars(value)

        # make sure user vars get expanded
        value = os.path.expanduser(value)

        # expand to absolute path
        value = os.path.abspath(value)

        valid = (os.path.exists(value)
                 or not self.require_exist) and not os.path.isdir(value)
        if not valid:
            raise ValidationError(self, path, value, "file does not exist")

        return value
예제 #9
0
파일: core.py 프로젝트: roysc/confu
 def validate(self, value, path, **kwargs):
     if value is None and self.default_is_none:
         return value
     try:
         value = float(value)
     except (TypeError, ValueError):
         raise ValidationError(self, path, value, "float expected")
     return super(Float, self).validate(value, path, **kwargs)
예제 #10
0
파일: core.py 프로젝트: 20c/confu
 def validate(self, value: float | str | None, path: list[str],
              **kwargs: Any) -> float | None:
     if value is None and self.default_is_none:
         return value
     try:
         value = float(value)
     except (TypeError, ValueError):
         raise ValidationError(self, path, value, "float expected")
     return super().validate(value, path, **kwargs)
예제 #11
0
파일: core.py 프로젝트: roysc/confu
 def validate(self, value, path, **kwargs):
     if isinstance(value, str):
         if value.lower() in self.true_values:
             value = True
         elif value.lower() in self.false_values:
             value = False
         else:
             raise ValidationError(self, path, value, "boolean expected")
     return super(Bool, self).validate(bool(value), path, **kwargs)
예제 #12
0
파일: core.py 프로젝트: 20c/confu
 def validate(self, value: int | str, path: list[str],
              **kwargs: Any) -> bool:
     if isinstance(value, str):
         if value.lower() in self.true_values:
             value = True
         elif value.lower() in self.false_values:
             value = False
         else:
             raise ValidationError(self, path, value, "boolean expected")
     return super().validate(bool(value), path, **kwargs)
예제 #13
0
    def validate(self, value: str | None, path: list[str],
                 **kwargs: Any) -> Any:
        value = super().validate(value, path, **kwargs)

        if value is None and self.default_is_none:
            return value

        if self.blank and value == "":
            return value

        value = f"{value}"
        value_v4 = self.validate_v4(value, path, **kwargs)
        value_v6 = self.validate_v6(value, path, **kwargs)
        if self.protocol == 4 and not value_v4:
            raise ValidationError(self, path, value, "invalid ip (v4)")
        elif self.protocol == 6 and not value_v6:
            raise ValidationError(self, path, value, "invalid ip (v6)")
        elif self.protocol is None and not value_v4 and not value_v6:
            raise ValidationError(self, path, value, "invalid ip (v4 or v6)")
        return value_v4 or value_v6
예제 #14
0
파일: core.py 프로젝트: 20c/confu
 def makedir(self, value: str, config_path: list[str]) -> None:
     try:
         os.makedirs(value, self.create)
     except Exception as err:
         raise ValidationError(
             self,
             config_path,
             value,
             "tried to create directory  but failed with error"
             ": {}".format(err),
         )
예제 #15
0
파일: core.py 프로젝트: 20c/confu
 def validate(
     self,
     value: types.TimeDuration | float | str | None,
     path: list[str],
     **kwargs: Any,
 ) -> TimeDuration:
     if value is None and self.default_is_none:
         return value
     try:
         value = types.TimeDuration(value)
     except (TypeError, ValueError):
         raise ValidationError(self, path, value, "TimeDuration expected")
     return super().validate(value, path, **kwargs)
예제 #16
0
    def validate(self, value: str | None, path: list[str],
                 **kwargs: Any) -> str | None:
        value = super().validate(value, path, **kwargs)

        if value == "" and self.blank:
            return value

        if value is None and self.default_is_none:
            return value

        # TODO: any reason to get more sophisticated than this?
        if not re.match(r"[^@\s]+@[^@\s]+", value):
            raise ValidationError(self, path, value, "email address expected")

        return value
예제 #17
0
def test_attribute(Class, value_pass, validated, value_fail, init):
    attribute = Class("test", **init)
    assert attribute.validate(value_pass, []) == validated
    if value_fail is not None:
        with pytest.raises(ValidationError):
            attribute.validate(value_fail, [])


@pytest.mark.parametrize(
    "SchemaClass,config_pass,config_fail,error",
    [
        (
            Schema_01,
            "nesting/success.json",
            "nesting/failure01.json",
            ValidationError(None, ["nested", "int_attr"], "test",
                            "integer expected"),
        ),
        (
            Schema_01,
            "nesting/success.json",
            "nesting/failure02.json",
            ValidationError(None, ["nested"], [1, 2, 3],
                            "dictionary expected"),
        ),
        (
            Schema_01,
            "nesting/success.json",
            "nesting/failure03.json",
            ValidationError(None, ["list_attr", 0], 1, "dictionary expected"),
        ),
        (