summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore1
-rw-r--r--python-cleand.spec396
-rw-r--r--sources1
3 files changed, 398 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore
index e69de29..5f78d19 100644
--- a/.gitignore
+++ b/.gitignore
@@ -0,0 +1 @@
+/cleand-1.3.1.tar.gz
diff --git a/python-cleand.spec b/python-cleand.spec
new file mode 100644
index 0000000..68d0b0c
--- /dev/null
+++ b/python-cleand.spec
@@ -0,0 +1,396 @@
+%global _empty_manifest_terminate_build 0
+Name: python-cleand
+Version: 1.3.1
+Release: 1
+Summary: a declarative data validator
+License: MIT License
+URL: https://github.com/saryou/cleaned
+Source0: https://mirrors.aliyun.com/pypi/web/packages/17/28/3b6a0d9b36297daf8b11b61d589216356b601fe4d53693a259a7940195e4/cleand-1.3.1.tar.gz
+BuildArch: noarch
+
+
+%description
+# cleaned
+
+pypi: https://pypi.org/project/cleand/
+
+(pypi's project name is not clean**e**d because it wasn't available then)
+
+## Overview
+
+`cleaned` is a declarative data validator.
+
+## Examples
+
+```python
+import json
+import cleaned as cl
+
+
+class Request(cl.Cleaned):
+ username = cl.Str(pattern='^[a-zA-Z_]+$', blank=False, min_length=3)
+ password = cl.Str(blank=False, min_length=8)
+ age = cl.Int()
+
+
+def register_user_api(request_json: str) -> ...:
+ dirty_data = json.loads(request_json)
+ cleaned_data = Request(**dirty_data)
+
+ # username matches ^[a-zA-Z_]+$ and it has at least 3 characters
+ username = cleaned_data.username
+
+ # password is at least 8 characters
+ password = cleaned_data.password
+
+ # age is a int value
+ age = cleaned_data.age
+
+ # do something with the data
+ print(username, password, age)
+ ...
+
+
+register_user_api(json.dumps({
+ 'username': 'user',
+ 'password': 'KJF83h9q3FAS',
+ 'age': '20',
+}))
+
+
+try:
+ Request(username='invalid format', password='short')
+except cl.ValidationError as e:
+ print(e.nested['username'])
+ # ('The value must match: ^[a-zA-Z_]+$', 'pattern')
+ print(e.nested['password'])
+ # ('The length of the value must be longer than or equal to 8.', 'min_length')
+ print(e.nested['age'])
+ # ('This field is required', 'required')
+```
+
+## Static Typing
+
+mypy can handle almost all cleaned values in the library.
+
+```python
+import cleaned as cl
+import enum
+
+
+class Examples(cl.Cleaned):
+ class NestedExample(cl.Cleaned):
+ a = cl.Int()
+
+ class EnumExample(enum.Enum):
+ a = 1
+ b = 2
+
+ a = cl.Either(cl.Int(), cl.Str(blank=False))
+ b = cl.Int().opt()
+ c = cl.Dict(key=cl.Int(), value=cl.Float().opt()).opt()
+ d = cl.Nested(NestedExample)
+ e = cl.Enum(EnumExample)
+ f = cl.List(cl.Nested(NestedExample))
+ g = cl.List(cl.Nested(lambda: Examples))
+
+
+ex = Examples()
+
+reveal_type(ex.a)
+# Revealed type is 'Union[builtins.int*, builtins.str*]'
+
+reveal_type(ex.b)
+# Revealed type is 'Union[builtins.int*, None]'
+
+reveal_type(ex.c)
+# Revealed type is 'Union[builtins.dict*[builtins.int*, Union[builtins.float*, None]], None]'
+
+reveal_type(ex.d)
+# Revealed type is 'Examples.NestedExample*'
+
+reveal_type(ex.e)
+# Revealed type is 'Examples.EnumExample*'
+
+reveal_type(ex.f)
+# Revealed type is 'builtins.list*[Examples.NestedExample*]'
+
+reveal_type(ex.g)
+# Revealed type is 'builtins.list*[hoge.Examples*]'
+```
+
+
+%package -n python3-cleand
+Summary: a declarative data validator
+Provides: python-cleand
+BuildRequires: python3-devel
+BuildRequires: python3-setuptools
+BuildRequires: python3-pip
+%description -n python3-cleand
+# cleaned
+
+pypi: https://pypi.org/project/cleand/
+
+(pypi's project name is not clean**e**d because it wasn't available then)
+
+## Overview
+
+`cleaned` is a declarative data validator.
+
+## Examples
+
+```python
+import json
+import cleaned as cl
+
+
+class Request(cl.Cleaned):
+ username = cl.Str(pattern='^[a-zA-Z_]+$', blank=False, min_length=3)
+ password = cl.Str(blank=False, min_length=8)
+ age = cl.Int()
+
+
+def register_user_api(request_json: str) -> ...:
+ dirty_data = json.loads(request_json)
+ cleaned_data = Request(**dirty_data)
+
+ # username matches ^[a-zA-Z_]+$ and it has at least 3 characters
+ username = cleaned_data.username
+
+ # password is at least 8 characters
+ password = cleaned_data.password
+
+ # age is a int value
+ age = cleaned_data.age
+
+ # do something with the data
+ print(username, password, age)
+ ...
+
+
+register_user_api(json.dumps({
+ 'username': 'user',
+ 'password': 'KJF83h9q3FAS',
+ 'age': '20',
+}))
+
+
+try:
+ Request(username='invalid format', password='short')
+except cl.ValidationError as e:
+ print(e.nested['username'])
+ # ('The value must match: ^[a-zA-Z_]+$', 'pattern')
+ print(e.nested['password'])
+ # ('The length of the value must be longer than or equal to 8.', 'min_length')
+ print(e.nested['age'])
+ # ('This field is required', 'required')
+```
+
+## Static Typing
+
+mypy can handle almost all cleaned values in the library.
+
+```python
+import cleaned as cl
+import enum
+
+
+class Examples(cl.Cleaned):
+ class NestedExample(cl.Cleaned):
+ a = cl.Int()
+
+ class EnumExample(enum.Enum):
+ a = 1
+ b = 2
+
+ a = cl.Either(cl.Int(), cl.Str(blank=False))
+ b = cl.Int().opt()
+ c = cl.Dict(key=cl.Int(), value=cl.Float().opt()).opt()
+ d = cl.Nested(NestedExample)
+ e = cl.Enum(EnumExample)
+ f = cl.List(cl.Nested(NestedExample))
+ g = cl.List(cl.Nested(lambda: Examples))
+
+
+ex = Examples()
+
+reveal_type(ex.a)
+# Revealed type is 'Union[builtins.int*, builtins.str*]'
+
+reveal_type(ex.b)
+# Revealed type is 'Union[builtins.int*, None]'
+
+reveal_type(ex.c)
+# Revealed type is 'Union[builtins.dict*[builtins.int*, Union[builtins.float*, None]], None]'
+
+reveal_type(ex.d)
+# Revealed type is 'Examples.NestedExample*'
+
+reveal_type(ex.e)
+# Revealed type is 'Examples.EnumExample*'
+
+reveal_type(ex.f)
+# Revealed type is 'builtins.list*[Examples.NestedExample*]'
+
+reveal_type(ex.g)
+# Revealed type is 'builtins.list*[hoge.Examples*]'
+```
+
+
+%package help
+Summary: Development documents and examples for cleand
+Provides: python3-cleand-doc
+%description help
+# cleaned
+
+pypi: https://pypi.org/project/cleand/
+
+(pypi's project name is not clean**e**d because it wasn't available then)
+
+## Overview
+
+`cleaned` is a declarative data validator.
+
+## Examples
+
+```python
+import json
+import cleaned as cl
+
+
+class Request(cl.Cleaned):
+ username = cl.Str(pattern='^[a-zA-Z_]+$', blank=False, min_length=3)
+ password = cl.Str(blank=False, min_length=8)
+ age = cl.Int()
+
+
+def register_user_api(request_json: str) -> ...:
+ dirty_data = json.loads(request_json)
+ cleaned_data = Request(**dirty_data)
+
+ # username matches ^[a-zA-Z_]+$ and it has at least 3 characters
+ username = cleaned_data.username
+
+ # password is at least 8 characters
+ password = cleaned_data.password
+
+ # age is a int value
+ age = cleaned_data.age
+
+ # do something with the data
+ print(username, password, age)
+ ...
+
+
+register_user_api(json.dumps({
+ 'username': 'user',
+ 'password': 'KJF83h9q3FAS',
+ 'age': '20',
+}))
+
+
+try:
+ Request(username='invalid format', password='short')
+except cl.ValidationError as e:
+ print(e.nested['username'])
+ # ('The value must match: ^[a-zA-Z_]+$', 'pattern')
+ print(e.nested['password'])
+ # ('The length of the value must be longer than or equal to 8.', 'min_length')
+ print(e.nested['age'])
+ # ('This field is required', 'required')
+```
+
+## Static Typing
+
+mypy can handle almost all cleaned values in the library.
+
+```python
+import cleaned as cl
+import enum
+
+
+class Examples(cl.Cleaned):
+ class NestedExample(cl.Cleaned):
+ a = cl.Int()
+
+ class EnumExample(enum.Enum):
+ a = 1
+ b = 2
+
+ a = cl.Either(cl.Int(), cl.Str(blank=False))
+ b = cl.Int().opt()
+ c = cl.Dict(key=cl.Int(), value=cl.Float().opt()).opt()
+ d = cl.Nested(NestedExample)
+ e = cl.Enum(EnumExample)
+ f = cl.List(cl.Nested(NestedExample))
+ g = cl.List(cl.Nested(lambda: Examples))
+
+
+ex = Examples()
+
+reveal_type(ex.a)
+# Revealed type is 'Union[builtins.int*, builtins.str*]'
+
+reveal_type(ex.b)
+# Revealed type is 'Union[builtins.int*, None]'
+
+reveal_type(ex.c)
+# Revealed type is 'Union[builtins.dict*[builtins.int*, Union[builtins.float*, None]], None]'
+
+reveal_type(ex.d)
+# Revealed type is 'Examples.NestedExample*'
+
+reveal_type(ex.e)
+# Revealed type is 'Examples.EnumExample*'
+
+reveal_type(ex.f)
+# Revealed type is 'builtins.list*[Examples.NestedExample*]'
+
+reveal_type(ex.g)
+# Revealed type is 'builtins.list*[hoge.Examples*]'
+```
+
+
+%prep
+%autosetup -n cleand-1.3.1
+
+%build
+%py3_build
+
+%install
+%py3_install
+install -d -m755 %{buildroot}/%{_pkgdocdir}
+if [ -d doc ]; then cp -arf doc %{buildroot}/%{_pkgdocdir}; fi
+if [ -d docs ]; then cp -arf docs %{buildroot}/%{_pkgdocdir}; fi
+if [ -d example ]; then cp -arf example %{buildroot}/%{_pkgdocdir}; fi
+if [ -d examples ]; then cp -arf examples %{buildroot}/%{_pkgdocdir}; fi
+pushd %{buildroot}
+if [ -d usr/lib ]; then
+ find usr/lib -type f -printf "\"/%h/%f\"\n" >> filelist.lst
+fi
+if [ -d usr/lib64 ]; then
+ find usr/lib64 -type f -printf "\"/%h/%f\"\n" >> filelist.lst
+fi
+if [ -d usr/bin ]; then
+ find usr/bin -type f -printf "\"/%h/%f\"\n" >> filelist.lst
+fi
+if [ -d usr/sbin ]; then
+ find usr/sbin -type f -printf "\"/%h/%f\"\n" >> filelist.lst
+fi
+touch doclist.lst
+if [ -d usr/share/man ]; then
+ find usr/share/man -type f -printf "\"/%h/%f.gz\"\n" >> doclist.lst
+fi
+popd
+mv %{buildroot}/filelist.lst .
+mv %{buildroot}/doclist.lst .
+
+%files -n python3-cleand -f filelist.lst
+%dir %{python3_sitelib}/*
+
+%files help -f doclist.lst
+%{_docdir}/*
+
+%changelog
+* Tue Jun 20 2023 Python_Bot <Python_Bot@openeuler.org> - 1.3.1-1
+- Package Spec generated
diff --git a/sources b/sources
new file mode 100644
index 0000000..e3a9f6f
--- /dev/null
+++ b/sources
@@ -0,0 +1 @@
+f7c25b3711449967922a72ee2c0eaa12 cleand-1.3.1.tar.gz