singlestoredb 1.14.2__cp38-abi3-win_amd64.whl → 1.15.1__cp38-abi3-win_amd64.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of singlestoredb might be problematic. Click here for more details.
- _singlestoredb_accel.pyd +0 -0
- singlestoredb/__init__.py +2 -2
- singlestoredb/ai/chat.py +14 -0
- singlestoredb/apps/_python_udfs.py +3 -3
- singlestoredb/config.py +11 -0
- singlestoredb/docstring/__init__.py +33 -0
- singlestoredb/docstring/attrdoc.py +126 -0
- singlestoredb/docstring/common.py +230 -0
- singlestoredb/docstring/epydoc.py +267 -0
- singlestoredb/docstring/google.py +412 -0
- singlestoredb/docstring/numpydoc.py +562 -0
- singlestoredb/docstring/parser.py +100 -0
- singlestoredb/docstring/py.typed +1 -0
- singlestoredb/docstring/rest.py +256 -0
- singlestoredb/docstring/tests/__init__.py +1 -0
- singlestoredb/docstring/tests/_pydoctor.py +21 -0
- singlestoredb/docstring/tests/test_epydoc.py +729 -0
- singlestoredb/docstring/tests/test_google.py +1007 -0
- singlestoredb/docstring/tests/test_numpydoc.py +1100 -0
- singlestoredb/docstring/tests/test_parse_from_object.py +109 -0
- singlestoredb/docstring/tests/test_parser.py +248 -0
- singlestoredb/docstring/tests/test_rest.py +547 -0
- singlestoredb/docstring/tests/test_util.py +70 -0
- singlestoredb/docstring/util.py +141 -0
- singlestoredb/functions/decorator.py +51 -31
- singlestoredb/functions/ext/asgi.py +381 -35
- singlestoredb/functions/ext/timer.py +98 -0
- singlestoredb/functions/signature.py +374 -241
- singlestoredb/functions/typing/numpy.py +20 -0
- singlestoredb/functions/typing/pandas.py +2 -0
- singlestoredb/functions/typing/polars.py +2 -0
- singlestoredb/functions/typing/pyarrow.py +2 -0
- singlestoredb/fusion/handlers/files.py +4 -4
- singlestoredb/fusion/handlers/models.py +1 -1
- singlestoredb/fusion/handlers/stage.py +4 -4
- singlestoredb/magics/run_personal.py +82 -1
- singlestoredb/magics/run_shared.py +82 -1
- singlestoredb/management/__init__.py +1 -0
- singlestoredb/management/cluster.py +1 -1
- singlestoredb/management/manager.py +15 -5
- singlestoredb/management/region.py +104 -2
- singlestoredb/management/workspace.py +174 -3
- singlestoredb/tests/ext_funcs/__init__.py +133 -55
- singlestoredb/tests/test.sql +22 -0
- singlestoredb/tests/test_connection.py +18 -8
- singlestoredb/tests/test_ext_func.py +90 -0
- singlestoredb/tests/test_management.py +190 -0
- singlestoredb/tests/test_udf.py +43 -15
- {singlestoredb-1.14.2.dist-info → singlestoredb-1.15.1.dist-info}/METADATA +1 -1
- {singlestoredb-1.14.2.dist-info → singlestoredb-1.15.1.dist-info}/RECORD +55 -31
- /singlestoredb/functions/{typing.py → typing/__init__.py} +0 -0
- {singlestoredb-1.14.2.dist-info → singlestoredb-1.15.1.dist-info}/LICENSE +0 -0
- {singlestoredb-1.14.2.dist-info → singlestoredb-1.15.1.dist-info}/WHEEL +0 -0
- {singlestoredb-1.14.2.dist-info → singlestoredb-1.15.1.dist-info}/entry_points.txt +0 -0
- {singlestoredb-1.14.2.dist-info → singlestoredb-1.15.1.dist-info}/top_level.txt +0 -0
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
"""Utility functions for working with docstrings."""
|
|
2
|
+
import typing as T
|
|
3
|
+
from collections import ChainMap
|
|
4
|
+
from inspect import Signature
|
|
5
|
+
from itertools import chain
|
|
6
|
+
|
|
7
|
+
from .common import DocstringMeta
|
|
8
|
+
from .common import DocstringParam
|
|
9
|
+
from .common import DocstringReturns # noqa: F401
|
|
10
|
+
from .common import DocstringStyle
|
|
11
|
+
from .common import RenderingStyle
|
|
12
|
+
from .parser import compose
|
|
13
|
+
from .parser import parse
|
|
14
|
+
|
|
15
|
+
_Func = T.Callable[..., T.Any]
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
def combine_docstrings(
|
|
19
|
+
*others: _Func,
|
|
20
|
+
exclude: T.Iterable[T.Type[DocstringMeta]] = (),
|
|
21
|
+
style: DocstringStyle = DocstringStyle.AUTO,
|
|
22
|
+
rendering_style: RenderingStyle = RenderingStyle.COMPACT,
|
|
23
|
+
) -> _Func:
|
|
24
|
+
"""A function decorator that parses the docstrings from `others`,
|
|
25
|
+
programmatically combines them with the parsed docstring of the decorated
|
|
26
|
+
function, and replaces the docstring of the decorated function with the
|
|
27
|
+
composed result. Only parameters that are part of the decorated functions
|
|
28
|
+
signature are included in the combined docstring. When multiple sources for
|
|
29
|
+
a parameter or docstring metadata exists then the decorator will first
|
|
30
|
+
default to the wrapped function's value (when available) and otherwise use
|
|
31
|
+
the rightmost definition from ``others``.
|
|
32
|
+
|
|
33
|
+
The following example illustrates its usage:
|
|
34
|
+
|
|
35
|
+
>>> def fun1(a, b, c, d):
|
|
36
|
+
... '''short_description: fun1
|
|
37
|
+
...
|
|
38
|
+
... :param a: fun1
|
|
39
|
+
... :param b: fun1
|
|
40
|
+
... :return: fun1
|
|
41
|
+
... '''
|
|
42
|
+
>>> def fun2(b, c, d, e):
|
|
43
|
+
... '''short_description: fun2
|
|
44
|
+
...
|
|
45
|
+
... long_description: fun2
|
|
46
|
+
...
|
|
47
|
+
... :param b: fun2
|
|
48
|
+
... :param c: fun2
|
|
49
|
+
... :param e: fun2
|
|
50
|
+
... '''
|
|
51
|
+
>>> @combine_docstrings(fun1, fun2)
|
|
52
|
+
>>> def decorated(a, b, c, d, e, f):
|
|
53
|
+
... '''
|
|
54
|
+
... :param e: decorated
|
|
55
|
+
... :param f: decorated
|
|
56
|
+
... '''
|
|
57
|
+
>>> print(decorated.__doc__)
|
|
58
|
+
short_description: fun2
|
|
59
|
+
<BLANKLINE>
|
|
60
|
+
long_description: fun2
|
|
61
|
+
<BLANKLINE>
|
|
62
|
+
:param a: fun1
|
|
63
|
+
:param b: fun1
|
|
64
|
+
:param c: fun2
|
|
65
|
+
:param e: fun2
|
|
66
|
+
:param f: decorated
|
|
67
|
+
:returns: fun1
|
|
68
|
+
>>> @combine_docstrings(fun1, fun2, exclude=[DocstringReturns])
|
|
69
|
+
>>> def decorated(a, b, c, d, e, f): pass
|
|
70
|
+
>>> print(decorated.__doc__)
|
|
71
|
+
short_description: fun2
|
|
72
|
+
<BLANKLINE>
|
|
73
|
+
long_description: fun2
|
|
74
|
+
<BLANKLINE>
|
|
75
|
+
:param a: fun1
|
|
76
|
+
:param b: fun1
|
|
77
|
+
:param c: fun2
|
|
78
|
+
:param e: fun2
|
|
79
|
+
|
|
80
|
+
:param others: callables from which to parse docstrings.
|
|
81
|
+
:param exclude: an iterable of ``DocstringMeta`` subclasses to exclude when
|
|
82
|
+
combining docstrings.
|
|
83
|
+
:param style: style composed docstring. The default will infer the style
|
|
84
|
+
from the decorated function.
|
|
85
|
+
:param rendering_style: The rendering style used to compose a docstring.
|
|
86
|
+
:return: the decorated function with a modified docstring.
|
|
87
|
+
"""
|
|
88
|
+
|
|
89
|
+
def wrapper(func: _Func) -> _Func:
|
|
90
|
+
sig = Signature.from_callable(func)
|
|
91
|
+
|
|
92
|
+
comb_doc = parse(func.__doc__ or '')
|
|
93
|
+
docs = [parse(other.__doc__ or '') for other in others] + [comb_doc]
|
|
94
|
+
params = dict(
|
|
95
|
+
ChainMap(
|
|
96
|
+
*(
|
|
97
|
+
{param.arg_name: param for param in doc.params}
|
|
98
|
+
for doc in docs
|
|
99
|
+
),
|
|
100
|
+
),
|
|
101
|
+
)
|
|
102
|
+
|
|
103
|
+
for doc in reversed(docs):
|
|
104
|
+
if not doc.short_description:
|
|
105
|
+
continue
|
|
106
|
+
comb_doc.short_description = doc.short_description
|
|
107
|
+
comb_doc.blank_after_short_description = (
|
|
108
|
+
doc.blank_after_short_description
|
|
109
|
+
)
|
|
110
|
+
break
|
|
111
|
+
|
|
112
|
+
for doc in reversed(docs):
|
|
113
|
+
if not doc.long_description:
|
|
114
|
+
continue
|
|
115
|
+
comb_doc.long_description = doc.long_description
|
|
116
|
+
comb_doc.blank_after_long_description = (
|
|
117
|
+
doc.blank_after_long_description
|
|
118
|
+
)
|
|
119
|
+
break
|
|
120
|
+
|
|
121
|
+
combined: T.Dict[T.Type[DocstringMeta], T.List[DocstringMeta]] = {}
|
|
122
|
+
for doc in docs:
|
|
123
|
+
metas: T.Dict[T.Type[DocstringMeta], T.List[DocstringMeta]] = {}
|
|
124
|
+
for meta in doc.meta:
|
|
125
|
+
meta_type = type(meta)
|
|
126
|
+
if meta_type in exclude:
|
|
127
|
+
continue
|
|
128
|
+
metas.setdefault(meta_type, []).append(meta)
|
|
129
|
+
for meta_type, meta_list in metas.items():
|
|
130
|
+
combined[meta_type] = meta_list
|
|
131
|
+
|
|
132
|
+
combined[DocstringParam] = [
|
|
133
|
+
params[name] for name in sig.parameters if name in params
|
|
134
|
+
]
|
|
135
|
+
comb_doc.meta = list(chain(*combined.values()))
|
|
136
|
+
func.__doc__ = compose(
|
|
137
|
+
comb_doc, style=style, rendering_style=rendering_style,
|
|
138
|
+
)
|
|
139
|
+
return func
|
|
140
|
+
|
|
141
|
+
return wrapper
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import asyncio
|
|
1
2
|
import functools
|
|
2
3
|
import inspect
|
|
3
4
|
from typing import Any
|
|
@@ -19,6 +20,7 @@ ParameterType = Union[
|
|
|
19
20
|
]
|
|
20
21
|
|
|
21
22
|
ReturnType = ParameterType
|
|
23
|
+
UDFType = Callable[..., Any]
|
|
22
24
|
|
|
23
25
|
|
|
24
26
|
def is_valid_type(obj: Any) -> bool:
|
|
@@ -43,23 +45,20 @@ def is_valid_type(obj: Any) -> bool:
|
|
|
43
45
|
return False
|
|
44
46
|
|
|
45
47
|
|
|
46
|
-
def
|
|
48
|
+
def is_sqlstr_callable(obj: Any) -> bool:
|
|
47
49
|
"""Check if the object is a valid callable for a parameter type."""
|
|
48
50
|
if not callable(obj):
|
|
49
51
|
return False
|
|
50
52
|
|
|
51
53
|
returns = utils.get_annotations(obj).get('return', None)
|
|
52
54
|
|
|
53
|
-
if inspect.isclass(returns) and issubclass(returns,
|
|
55
|
+
if inspect.isclass(returns) and issubclass(returns, SQLString):
|
|
54
56
|
return True
|
|
55
57
|
|
|
56
|
-
|
|
57
|
-
f'callable {obj} must return a str, '
|
|
58
|
-
f'but got {returns}',
|
|
59
|
-
)
|
|
58
|
+
return False
|
|
60
59
|
|
|
61
60
|
|
|
62
|
-
def expand_types(args: Any) -> Optional[
|
|
61
|
+
def expand_types(args: Any) -> Optional[List[Any]]:
|
|
63
62
|
"""Expand the types for the function arguments / return values."""
|
|
64
63
|
if args is None:
|
|
65
64
|
return None
|
|
@@ -68,28 +67,32 @@ def expand_types(args: Any) -> Optional[Union[List[str], Type[Any]]]:
|
|
|
68
67
|
if isinstance(args, str):
|
|
69
68
|
return [args]
|
|
70
69
|
|
|
71
|
-
# General way of accepting pydantic.BaseModel, NamedTuple, TypedDict
|
|
72
|
-
elif is_valid_type(args):
|
|
73
|
-
return args
|
|
74
|
-
|
|
75
70
|
# List of SQL strings or callables
|
|
76
71
|
elif isinstance(args, list):
|
|
77
|
-
new_args = []
|
|
72
|
+
new_args: List[Any] = []
|
|
78
73
|
for arg in args:
|
|
79
74
|
if isinstance(arg, str):
|
|
80
75
|
new_args.append(arg)
|
|
81
|
-
elif
|
|
76
|
+
elif is_sqlstr_callable(arg):
|
|
82
77
|
new_args.append(arg())
|
|
78
|
+
elif type(arg) is type:
|
|
79
|
+
new_args.append(arg)
|
|
80
|
+
elif is_valid_type(arg):
|
|
81
|
+
new_args.append(arg)
|
|
83
82
|
else:
|
|
84
83
|
raise TypeError(f'unrecognized type for parameter: {arg}')
|
|
85
84
|
return new_args
|
|
86
85
|
|
|
87
86
|
# Callable that returns a SQL string
|
|
88
|
-
elif
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
87
|
+
elif is_sqlstr_callable(args):
|
|
88
|
+
return [args()]
|
|
89
|
+
|
|
90
|
+
# General way of accepting pydantic.BaseModel, NamedTuple, TypedDict
|
|
91
|
+
elif is_valid_type(args):
|
|
92
|
+
return [args]
|
|
93
|
+
|
|
94
|
+
elif type(args) is type:
|
|
95
|
+
return [args]
|
|
93
96
|
|
|
94
97
|
raise TypeError(f'unrecognized type for parameter: {args}')
|
|
95
98
|
|
|
@@ -100,7 +103,8 @@ def _func(
|
|
|
100
103
|
name: Optional[str] = None,
|
|
101
104
|
args: Optional[ParameterType] = None,
|
|
102
105
|
returns: Optional[ReturnType] = None,
|
|
103
|
-
|
|
106
|
+
timeout: Optional[int] = None,
|
|
107
|
+
) -> UDFType:
|
|
104
108
|
"""Generic wrapper for UDF and TVF decorators."""
|
|
105
109
|
|
|
106
110
|
_singlestoredb_attrs = { # type: ignore
|
|
@@ -108,6 +112,7 @@ def _func(
|
|
|
108
112
|
name=name,
|
|
109
113
|
args=expand_types(args),
|
|
110
114
|
returns=expand_types(returns),
|
|
115
|
+
timeout=timeout,
|
|
111
116
|
).items() if v is not None
|
|
112
117
|
}
|
|
113
118
|
|
|
@@ -115,23 +120,33 @@ def _func(
|
|
|
115
120
|
# called later, so the wrapper much be created with the func passed
|
|
116
121
|
# in at that time.
|
|
117
122
|
if func is None:
|
|
118
|
-
def decorate(func:
|
|
119
|
-
|
|
120
|
-
def wrapper(*args: Any, **kwargs: Any) -> Callable[..., Any]:
|
|
121
|
-
return func(*args, **kwargs) # type: ignore
|
|
123
|
+
def decorate(func: UDFType) -> UDFType:
|
|
122
124
|
|
|
123
|
-
|
|
125
|
+
if asyncio.iscoroutinefunction(func):
|
|
126
|
+
async def async_wrapper(*args: Any, **kwargs: Any) -> UDFType:
|
|
127
|
+
return await func(*args, **kwargs) # type: ignore
|
|
128
|
+
async_wrapper._singlestoredb_attrs = _singlestoredb_attrs # type: ignore
|
|
129
|
+
return functools.wraps(func)(async_wrapper)
|
|
124
130
|
|
|
125
|
-
|
|
131
|
+
else:
|
|
132
|
+
def wrapper(*args: Any, **kwargs: Any) -> UDFType:
|
|
133
|
+
return func(*args, **kwargs) # type: ignore
|
|
134
|
+
wrapper._singlestoredb_attrs = _singlestoredb_attrs # type: ignore
|
|
135
|
+
return functools.wraps(func)(wrapper)
|
|
126
136
|
|
|
127
137
|
return decorate
|
|
128
138
|
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
139
|
+
if asyncio.iscoroutinefunction(func):
|
|
140
|
+
async def async_wrapper(*args: Any, **kwargs: Any) -> UDFType:
|
|
141
|
+
return await func(*args, **kwargs) # type: ignore
|
|
142
|
+
async_wrapper._singlestoredb_attrs = _singlestoredb_attrs # type: ignore
|
|
143
|
+
return functools.wraps(func)(async_wrapper)
|
|
133
144
|
|
|
134
|
-
|
|
145
|
+
else:
|
|
146
|
+
def wrapper(*args: Any, **kwargs: Any) -> UDFType:
|
|
147
|
+
return func(*args, **kwargs) # type: ignore
|
|
148
|
+
wrapper._singlestoredb_attrs = _singlestoredb_attrs # type: ignore
|
|
149
|
+
return functools.wraps(func)(wrapper)
|
|
135
150
|
|
|
136
151
|
|
|
137
152
|
def udf(
|
|
@@ -140,7 +155,8 @@ def udf(
|
|
|
140
155
|
name: Optional[str] = None,
|
|
141
156
|
args: Optional[ParameterType] = None,
|
|
142
157
|
returns: Optional[ReturnType] = None,
|
|
143
|
-
|
|
158
|
+
timeout: Optional[int] = None,
|
|
159
|
+
) -> UDFType:
|
|
144
160
|
"""
|
|
145
161
|
Define a user-defined function (UDF).
|
|
146
162
|
|
|
@@ -167,6 +183,9 @@ def udf(
|
|
|
167
183
|
Specifies the return data type of the function. This parameter
|
|
168
184
|
works the same way as `args`. If the function is a table-valued
|
|
169
185
|
function, the return type should be a `Table` object.
|
|
186
|
+
timeout : int, optional
|
|
187
|
+
The timeout in seconds for the UDF execution. If not specified,
|
|
188
|
+
the global default timeout is used.
|
|
170
189
|
|
|
171
190
|
Returns
|
|
172
191
|
-------
|
|
@@ -178,4 +197,5 @@ def udf(
|
|
|
178
197
|
name=name,
|
|
179
198
|
args=args,
|
|
180
199
|
returns=returns,
|
|
200
|
+
timeout=timeout,
|
|
181
201
|
)
|