prefect-client 2.19.3__py3-none-any.whl → 3.0.0rc1__py3-none-any.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.
Files changed (239) hide show
  1. prefect/__init__.py +8 -56
  2. prefect/_internal/compatibility/deprecated.py +6 -115
  3. prefect/_internal/compatibility/experimental.py +4 -79
  4. prefect/_internal/concurrency/api.py +0 -34
  5. prefect/_internal/concurrency/calls.py +0 -6
  6. prefect/_internal/concurrency/cancellation.py +0 -3
  7. prefect/_internal/concurrency/event_loop.py +0 -20
  8. prefect/_internal/concurrency/inspection.py +3 -3
  9. prefect/_internal/concurrency/threads.py +35 -0
  10. prefect/_internal/concurrency/waiters.py +0 -28
  11. prefect/_internal/pydantic/__init__.py +0 -45
  12. prefect/_internal/pydantic/v1_schema.py +21 -22
  13. prefect/_internal/pydantic/v2_schema.py +0 -2
  14. prefect/_internal/pydantic/v2_validated_func.py +18 -23
  15. prefect/_internal/schemas/bases.py +44 -177
  16. prefect/_internal/schemas/fields.py +1 -43
  17. prefect/_internal/schemas/validators.py +60 -158
  18. prefect/artifacts.py +161 -14
  19. prefect/automations.py +39 -4
  20. prefect/blocks/abstract.py +1 -1
  21. prefect/blocks/core.py +268 -148
  22. prefect/blocks/fields.py +2 -57
  23. prefect/blocks/kubernetes.py +8 -12
  24. prefect/blocks/notifications.py +40 -20
  25. prefect/blocks/system.py +22 -11
  26. prefect/blocks/webhook.py +2 -9
  27. prefect/client/base.py +4 -4
  28. prefect/client/cloud.py +8 -13
  29. prefect/client/orchestration.py +347 -341
  30. prefect/client/schemas/actions.py +92 -86
  31. prefect/client/schemas/filters.py +20 -40
  32. prefect/client/schemas/objects.py +147 -145
  33. prefect/client/schemas/responses.py +16 -24
  34. prefect/client/schemas/schedules.py +47 -35
  35. prefect/client/subscriptions.py +2 -2
  36. prefect/client/utilities.py +5 -2
  37. prefect/concurrency/asyncio.py +3 -1
  38. prefect/concurrency/events.py +1 -1
  39. prefect/concurrency/services.py +6 -3
  40. prefect/context.py +195 -27
  41. prefect/deployments/__init__.py +5 -6
  42. prefect/deployments/base.py +7 -5
  43. prefect/deployments/flow_runs.py +185 -0
  44. prefect/deployments/runner.py +50 -45
  45. prefect/deployments/schedules.py +28 -23
  46. prefect/deployments/steps/__init__.py +0 -1
  47. prefect/deployments/steps/core.py +1 -0
  48. prefect/deployments/steps/pull.py +7 -21
  49. prefect/engine.py +12 -2422
  50. prefect/events/actions.py +17 -23
  51. prefect/events/cli/automations.py +19 -6
  52. prefect/events/clients.py +14 -37
  53. prefect/events/filters.py +14 -18
  54. prefect/events/related.py +2 -2
  55. prefect/events/schemas/__init__.py +0 -5
  56. prefect/events/schemas/automations.py +55 -46
  57. prefect/events/schemas/deployment_triggers.py +7 -197
  58. prefect/events/schemas/events.py +34 -65
  59. prefect/events/schemas/labelling.py +10 -14
  60. prefect/events/utilities.py +2 -3
  61. prefect/events/worker.py +2 -3
  62. prefect/filesystems.py +6 -517
  63. prefect/{new_flow_engine.py → flow_engine.py} +313 -72
  64. prefect/flow_runs.py +377 -5
  65. prefect/flows.py +248 -165
  66. prefect/futures.py +186 -345
  67. prefect/infrastructure/__init__.py +0 -27
  68. prefect/infrastructure/provisioners/__init__.py +5 -3
  69. prefect/infrastructure/provisioners/cloud_run.py +11 -6
  70. prefect/infrastructure/provisioners/container_instance.py +11 -7
  71. prefect/infrastructure/provisioners/ecs.py +6 -4
  72. prefect/infrastructure/provisioners/modal.py +8 -5
  73. prefect/input/actions.py +2 -4
  74. prefect/input/run_input.py +5 -7
  75. prefect/logging/formatters.py +0 -2
  76. prefect/logging/handlers.py +3 -11
  77. prefect/logging/loggers.py +2 -2
  78. prefect/manifests.py +2 -1
  79. prefect/records/__init__.py +1 -0
  80. prefect/records/result_store.py +42 -0
  81. prefect/records/store.py +9 -0
  82. prefect/results.py +43 -39
  83. prefect/runner/runner.py +9 -9
  84. prefect/runner/server.py +6 -10
  85. prefect/runner/storage.py +3 -8
  86. prefect/runner/submit.py +2 -2
  87. prefect/runner/utils.py +2 -2
  88. prefect/serializers.py +24 -35
  89. prefect/server/api/collections_data/views/aggregate-worker-metadata.json +5 -14
  90. prefect/settings.py +70 -133
  91. prefect/states.py +17 -47
  92. prefect/task_engine.py +697 -58
  93. prefect/task_runners.py +269 -301
  94. prefect/task_server.py +53 -34
  95. prefect/tasks.py +327 -337
  96. prefect/transactions.py +220 -0
  97. prefect/types/__init__.py +61 -82
  98. prefect/utilities/asyncutils.py +195 -136
  99. prefect/utilities/callables.py +121 -41
  100. prefect/utilities/collections.py +23 -38
  101. prefect/utilities/dispatch.py +11 -3
  102. prefect/utilities/dockerutils.py +4 -0
  103. prefect/utilities/engine.py +140 -20
  104. prefect/utilities/importtools.py +26 -27
  105. prefect/utilities/pydantic.py +128 -38
  106. prefect/utilities/schema_tools/hydration.py +5 -1
  107. prefect/utilities/templating.py +12 -2
  108. prefect/variables.py +78 -61
  109. prefect/workers/__init__.py +0 -1
  110. prefect/workers/base.py +15 -17
  111. prefect/workers/process.py +3 -8
  112. prefect/workers/server.py +2 -2
  113. {prefect_client-2.19.3.dist-info → prefect_client-3.0.0rc1.dist-info}/METADATA +22 -21
  114. prefect_client-3.0.0rc1.dist-info/RECORD +176 -0
  115. prefect/_internal/pydantic/_base_model.py +0 -51
  116. prefect/_internal/pydantic/_compat.py +0 -82
  117. prefect/_internal/pydantic/_flags.py +0 -20
  118. prefect/_internal/pydantic/_types.py +0 -8
  119. prefect/_internal/pydantic/utilities/__init__.py +0 -0
  120. prefect/_internal/pydantic/utilities/config_dict.py +0 -72
  121. prefect/_internal/pydantic/utilities/field_validator.py +0 -150
  122. prefect/_internal/pydantic/utilities/model_construct.py +0 -56
  123. prefect/_internal/pydantic/utilities/model_copy.py +0 -55
  124. prefect/_internal/pydantic/utilities/model_dump.py +0 -136
  125. prefect/_internal/pydantic/utilities/model_dump_json.py +0 -112
  126. prefect/_internal/pydantic/utilities/model_fields.py +0 -50
  127. prefect/_internal/pydantic/utilities/model_fields_set.py +0 -29
  128. prefect/_internal/pydantic/utilities/model_json_schema.py +0 -82
  129. prefect/_internal/pydantic/utilities/model_rebuild.py +0 -80
  130. prefect/_internal/pydantic/utilities/model_validate.py +0 -75
  131. prefect/_internal/pydantic/utilities/model_validate_json.py +0 -68
  132. prefect/_internal/pydantic/utilities/model_validator.py +0 -87
  133. prefect/_internal/pydantic/utilities/type_adapter.py +0 -71
  134. prefect/_vendor/__init__.py +0 -0
  135. prefect/_vendor/fastapi/__init__.py +0 -25
  136. prefect/_vendor/fastapi/applications.py +0 -946
  137. prefect/_vendor/fastapi/background.py +0 -3
  138. prefect/_vendor/fastapi/concurrency.py +0 -44
  139. prefect/_vendor/fastapi/datastructures.py +0 -58
  140. prefect/_vendor/fastapi/dependencies/__init__.py +0 -0
  141. prefect/_vendor/fastapi/dependencies/models.py +0 -64
  142. prefect/_vendor/fastapi/dependencies/utils.py +0 -877
  143. prefect/_vendor/fastapi/encoders.py +0 -177
  144. prefect/_vendor/fastapi/exception_handlers.py +0 -40
  145. prefect/_vendor/fastapi/exceptions.py +0 -46
  146. prefect/_vendor/fastapi/logger.py +0 -3
  147. prefect/_vendor/fastapi/middleware/__init__.py +0 -1
  148. prefect/_vendor/fastapi/middleware/asyncexitstack.py +0 -25
  149. prefect/_vendor/fastapi/middleware/cors.py +0 -3
  150. prefect/_vendor/fastapi/middleware/gzip.py +0 -3
  151. prefect/_vendor/fastapi/middleware/httpsredirect.py +0 -3
  152. prefect/_vendor/fastapi/middleware/trustedhost.py +0 -3
  153. prefect/_vendor/fastapi/middleware/wsgi.py +0 -3
  154. prefect/_vendor/fastapi/openapi/__init__.py +0 -0
  155. prefect/_vendor/fastapi/openapi/constants.py +0 -2
  156. prefect/_vendor/fastapi/openapi/docs.py +0 -203
  157. prefect/_vendor/fastapi/openapi/models.py +0 -480
  158. prefect/_vendor/fastapi/openapi/utils.py +0 -485
  159. prefect/_vendor/fastapi/param_functions.py +0 -340
  160. prefect/_vendor/fastapi/params.py +0 -453
  161. prefect/_vendor/fastapi/requests.py +0 -4
  162. prefect/_vendor/fastapi/responses.py +0 -40
  163. prefect/_vendor/fastapi/routing.py +0 -1331
  164. prefect/_vendor/fastapi/security/__init__.py +0 -15
  165. prefect/_vendor/fastapi/security/api_key.py +0 -98
  166. prefect/_vendor/fastapi/security/base.py +0 -6
  167. prefect/_vendor/fastapi/security/http.py +0 -172
  168. prefect/_vendor/fastapi/security/oauth2.py +0 -227
  169. prefect/_vendor/fastapi/security/open_id_connect_url.py +0 -34
  170. prefect/_vendor/fastapi/security/utils.py +0 -10
  171. prefect/_vendor/fastapi/staticfiles.py +0 -1
  172. prefect/_vendor/fastapi/templating.py +0 -3
  173. prefect/_vendor/fastapi/testclient.py +0 -1
  174. prefect/_vendor/fastapi/types.py +0 -3
  175. prefect/_vendor/fastapi/utils.py +0 -235
  176. prefect/_vendor/fastapi/websockets.py +0 -7
  177. prefect/_vendor/starlette/__init__.py +0 -1
  178. prefect/_vendor/starlette/_compat.py +0 -28
  179. prefect/_vendor/starlette/_exception_handler.py +0 -80
  180. prefect/_vendor/starlette/_utils.py +0 -88
  181. prefect/_vendor/starlette/applications.py +0 -261
  182. prefect/_vendor/starlette/authentication.py +0 -159
  183. prefect/_vendor/starlette/background.py +0 -43
  184. prefect/_vendor/starlette/concurrency.py +0 -59
  185. prefect/_vendor/starlette/config.py +0 -151
  186. prefect/_vendor/starlette/convertors.py +0 -87
  187. prefect/_vendor/starlette/datastructures.py +0 -707
  188. prefect/_vendor/starlette/endpoints.py +0 -130
  189. prefect/_vendor/starlette/exceptions.py +0 -60
  190. prefect/_vendor/starlette/formparsers.py +0 -276
  191. prefect/_vendor/starlette/middleware/__init__.py +0 -17
  192. prefect/_vendor/starlette/middleware/authentication.py +0 -52
  193. prefect/_vendor/starlette/middleware/base.py +0 -220
  194. prefect/_vendor/starlette/middleware/cors.py +0 -176
  195. prefect/_vendor/starlette/middleware/errors.py +0 -265
  196. prefect/_vendor/starlette/middleware/exceptions.py +0 -74
  197. prefect/_vendor/starlette/middleware/gzip.py +0 -113
  198. prefect/_vendor/starlette/middleware/httpsredirect.py +0 -19
  199. prefect/_vendor/starlette/middleware/sessions.py +0 -82
  200. prefect/_vendor/starlette/middleware/trustedhost.py +0 -64
  201. prefect/_vendor/starlette/middleware/wsgi.py +0 -147
  202. prefect/_vendor/starlette/requests.py +0 -328
  203. prefect/_vendor/starlette/responses.py +0 -347
  204. prefect/_vendor/starlette/routing.py +0 -933
  205. prefect/_vendor/starlette/schemas.py +0 -154
  206. prefect/_vendor/starlette/staticfiles.py +0 -248
  207. prefect/_vendor/starlette/status.py +0 -199
  208. prefect/_vendor/starlette/templating.py +0 -231
  209. prefect/_vendor/starlette/testclient.py +0 -804
  210. prefect/_vendor/starlette/types.py +0 -30
  211. prefect/_vendor/starlette/websockets.py +0 -193
  212. prefect/agent.py +0 -698
  213. prefect/deployments/deployments.py +0 -1042
  214. prefect/deprecated/__init__.py +0 -0
  215. prefect/deprecated/data_documents.py +0 -350
  216. prefect/deprecated/packaging/__init__.py +0 -12
  217. prefect/deprecated/packaging/base.py +0 -96
  218. prefect/deprecated/packaging/docker.py +0 -146
  219. prefect/deprecated/packaging/file.py +0 -92
  220. prefect/deprecated/packaging/orion.py +0 -80
  221. prefect/deprecated/packaging/serializers.py +0 -171
  222. prefect/events/instrument.py +0 -135
  223. prefect/infrastructure/base.py +0 -323
  224. prefect/infrastructure/container.py +0 -818
  225. prefect/infrastructure/kubernetes.py +0 -920
  226. prefect/infrastructure/process.py +0 -289
  227. prefect/new_task_engine.py +0 -423
  228. prefect/pydantic/__init__.py +0 -76
  229. prefect/pydantic/main.py +0 -39
  230. prefect/software/__init__.py +0 -2
  231. prefect/software/base.py +0 -50
  232. prefect/software/conda.py +0 -199
  233. prefect/software/pip.py +0 -122
  234. prefect/software/python.py +0 -52
  235. prefect/workers/block.py +0 -218
  236. prefect_client-2.19.3.dist-info/RECORD +0 -292
  237. {prefect_client-2.19.3.dist-info → prefect_client-3.0.0rc1.dist-info}/LICENSE +0 -0
  238. {prefect_client-2.19.3.dist-info → prefect_client-3.0.0rc1.dist-info}/WHEEL +0 -0
  239. {prefect_client-2.19.3.dist-info → prefect_client-3.0.0rc1.dist-info}/top_level.txt +0 -0
File without changes
@@ -1,350 +0,0 @@
1
- import base64
2
- import json
3
- import uuid
4
- import warnings
5
- from typing import (
6
- TYPE_CHECKING,
7
- Any,
8
- Dict,
9
- Generic,
10
- Iterable,
11
- Tuple,
12
- Type,
13
- TypeVar,
14
- Union,
15
- )
16
-
17
- import cloudpickle
18
-
19
- from prefect._internal.pydantic import HAS_PYDANTIC_V2
20
-
21
- if HAS_PYDANTIC_V2:
22
- import pydantic.v1 as pydantic
23
- else:
24
- import pydantic
25
-
26
- from typing_extensions import Protocol
27
-
28
- from prefect._internal.compatibility.deprecated import (
29
- deprecated_callable,
30
- generate_deprecation_message,
31
- )
32
- from prefect._internal.schemas.bases import PrefectBaseModel
33
-
34
- if TYPE_CHECKING:
35
- from prefect.deprecated.packaging.base import PackageManifest
36
-
37
- T = TypeVar("T", bound="DataDocument") # Generic for DataDocument class types
38
- D = TypeVar("D", bound=Any) # Generic for DataDocument data types
39
-
40
-
41
- _SERIALIZERS: Dict[str, "Serializer"] = {}
42
-
43
-
44
- class Serializer(Protocol[D]):
45
- """
46
- Define a serializer that can encode data of type 'D' into bytes
47
- """
48
-
49
- @staticmethod
50
- def dumps(data: D, **kwargs: Any) -> bytes:
51
- raise NotImplementedError
52
-
53
- @staticmethod
54
- def loads(blob: bytes) -> D:
55
- raise NotImplementedError
56
-
57
-
58
- def register_serializer(
59
- encoding: Union[str, Tuple[str, ...]], serializer: Serializer = None
60
- ):
61
- """Register dispatch of `func` on arguments of encoding `encoding`"""
62
-
63
- def wrapper(serializer):
64
- if isinstance(encoding, tuple):
65
- for e in encoding:
66
- register_serializer(e, serializer)
67
- else:
68
- _SERIALIZERS[encoding] = serializer
69
- return serializer
70
-
71
- return wrapper(serializer) if serializer is not None else wrapper
72
-
73
-
74
- def lookup_serializer(encoding: str) -> Serializer:
75
- """Return the serializer implementation for the given ``encoding``"""
76
- try:
77
- return _SERIALIZERS[encoding]
78
- except KeyError:
79
- raise ValueError(f"Unregistered encoding {encoding!r}")
80
-
81
-
82
- class DataDocument(PrefectBaseModel, Generic[D]):
83
- """
84
- A data document includes an encoding string and a blob of encoded data
85
-
86
- Subclasses can define the expected type for the blob's underlying type using the
87
- generic variable `D`.
88
-
89
- For example `DataDocument[str]` indicates that a string should be passed when
90
- creating the document and a string will be returned when it is decoded.
91
- """
92
-
93
- encoding: str
94
- blob: bytes
95
-
96
- # A cache for the decoded data, see `DataDocument.decode`
97
- _data: D
98
- __slots__ = ["_data"]
99
-
100
- @classmethod
101
- @deprecated_callable(
102
- start_date="Sep 2022",
103
- help="Data documents should not be created. Use result persistence instead.",
104
- )
105
- def encode(
106
- cls: Type["DataDocument"], encoding: str, data: D, **kwargs: Any
107
- ) -> "DataDocument[D]":
108
- """
109
- Create a new data document
110
-
111
- A serializer must be registered for the given `encoding`
112
- """
113
- # Dispatch encoding
114
- blob = lookup_serializer(encoding).dumps(data, **kwargs)
115
-
116
- inst = cls(blob=blob, encoding=encoding)
117
- inst._cache_data(data)
118
- return inst
119
-
120
- def decode(self) -> D:
121
- """
122
- Get the data from a data document
123
-
124
- A serializer must be registered for the document's encoding
125
- """
126
- if self.has_cached_data():
127
- return self._data
128
-
129
- # Dispatch decoding
130
- data = lookup_serializer(self.encoding).loads(self.blob)
131
-
132
- self._cache_data(data)
133
- return data
134
-
135
- def _cache_data(self, data) -> None:
136
- # Use object's setattr to avoid a pydantic 'field does not exist' error
137
- # See https://github.com/samuelcolvin/pydantic/issues/655
138
- object.__setattr__(self, "_data", data)
139
-
140
- def has_cached_data(self):
141
- return hasattr(self, "_data")
142
-
143
- def __str__(self) -> str:
144
- if self.has_cached_data():
145
- return repr(self._data)
146
- else:
147
- return repr(self)
148
-
149
- def __repr__(self) -> str:
150
- return f"{type(self).__name__}(encoding={self.encoding!r})"
151
-
152
-
153
- @register_serializer("json")
154
- class DocumentJSONSerializer:
155
- """
156
- Serializes data to JSON.
157
-
158
- Input types must be compatible with the stdlib json library.
159
-
160
- Wraps the `json` library to serialize to UTF-8 bytes instead of string types.
161
- """
162
-
163
- @staticmethod
164
- @deprecated_callable(
165
- start_date="Sep 2022",
166
- help=(
167
- "Data document serializers should not be used. Use result serializers"
168
- " instead."
169
- ),
170
- )
171
- def dumps(data: Any) -> bytes:
172
- return json.dumps(data).encode()
173
-
174
- @staticmethod
175
- def loads(blob: bytes) -> Any:
176
- return json.loads(blob.decode())
177
-
178
-
179
- @register_serializer("text")
180
- class TextSerializer:
181
- @staticmethod
182
- @deprecated_callable(
183
- start_date="Sep 2022",
184
- help=(
185
- "Data document serializers should not be used. Use result serializers"
186
- " instead."
187
- ),
188
- )
189
- def dumps(data: str) -> bytes:
190
- return data.encode()
191
-
192
- @staticmethod
193
- def loads(blob: bytes) -> str:
194
- return blob.decode()
195
-
196
-
197
- @register_serializer("cloudpickle")
198
- class DocumentPickleSerializer:
199
- """
200
- Serializes arbitrary objects using the pickle protocol.
201
-
202
- Wraps `cloudpickle` to encode bytes in base64 for safe transmission.
203
- """
204
-
205
- @staticmethod
206
- @deprecated_callable(
207
- start_date="Sep 2022",
208
- help=(
209
- "Data document serializers should not be used. Use result serializers"
210
- " instead."
211
- ),
212
- )
213
- def dumps(data: Any) -> bytes:
214
- data_bytes = cloudpickle.dumps(data)
215
-
216
- return base64.encodebytes(data_bytes)
217
-
218
- @staticmethod
219
- def loads(blob: bytes) -> Any:
220
- return cloudpickle.loads(base64.decodebytes(blob))
221
- # TODO: Consider adding python version data to pickle payloads to raise
222
- # more helpful errors for users.
223
- # A TypeError("expected bytes-like object, not int") will be raised if
224
- # a document is deserialized by Python 3.7 and serialized by 3.8+
225
-
226
-
227
- @register_serializer("package-manifest")
228
- class PackageManifestSerializer:
229
- """
230
- Serializes a package manifest.
231
- """
232
-
233
- @staticmethod
234
- @deprecated_callable(
235
- start_date="Sep 2022",
236
- help=(
237
- "Data document serializers should not be used. Use result serializers"
238
- " instead."
239
- ),
240
- )
241
- def dumps(data: "PackageManifest") -> bytes:
242
- return data.json().encode()
243
-
244
- @staticmethod
245
- def loads(blob: bytes) -> "PackageManifest":
246
- from prefect.deprecated.packaging.base import PackageManifest
247
-
248
- return PackageManifest.parse_raw(blob)
249
-
250
-
251
- @register_serializer("result")
252
- class ResultSerializer:
253
- """
254
- Serializes a result object
255
- """
256
-
257
- @staticmethod
258
- @deprecated_callable(
259
- start_date="Sep 2022",
260
- help=(
261
- "Data document serializers should not be used. Use result serializers"
262
- " instead."
263
- ),
264
- )
265
- def dumps(data: "_Result") -> bytes:
266
- return data.json().encode()
267
-
268
- @staticmethod
269
- def loads(blob: bytes) -> "_Result":
270
- return _Result.parse_raw(blob)
271
-
272
-
273
- def result_from_state_with_data_document(state, raise_on_failure: bool) -> Any:
274
- # Complain about usage
275
- warnings.warn(
276
- generate_deprecation_message(
277
- "Retrieving results from states with data documents", start_date="Sep 2022"
278
- ),
279
- DeprecationWarning,
280
- stacklevel=3,
281
- )
282
-
283
- data = None
284
-
285
- if state.data:
286
- data = state.data.decode()
287
-
288
- from prefect.states import State
289
-
290
- if (
291
- state.is_failed() or state.is_crashed() or state.is_cancelled()
292
- ) and raise_on_failure:
293
- if isinstance(data, Exception):
294
- raise data
295
- elif isinstance(data, BaseException):
296
- warnings.warn(
297
- f"State result is a {type(data).__name__!r} type and is not safe "
298
- "to re-raise, it will be returned instead."
299
- )
300
- return data
301
- elif isinstance(data, State):
302
- data.result(fetch=False)
303
- elif isinstance(data, Iterable) and all([isinstance(o, State) for o in data]):
304
- # raise the first failure we find
305
- for state in data:
306
- state.result(fetch=False)
307
-
308
- # we don't make this an else in case any of the above conditionals doesn't raise
309
- raise TypeError(
310
- f"Unexpected result for failure state: {data!r} —— "
311
- f"{type(data).__name__} cannot be resolved into an exception"
312
- )
313
-
314
- return data
315
-
316
-
317
- async def _persist_serialized_result(
318
- content: bytes,
319
- filesystem,
320
- ) -> DataDocument:
321
- key = uuid.uuid4().hex
322
- await filesystem.write_path(key, content)
323
- result = _Result(key=key, filesystem_document_id=filesystem._block_document_id)
324
- return DataDocument.encode("result", result)
325
-
326
-
327
- async def _retrieve_serialized_result(document: DataDocument, client) -> bytes:
328
- from prefect.blocks.core import Block
329
-
330
- if document.encoding != "result":
331
- raise TypeError(
332
- f"Got unsupported data document encoding of {document.encoding!r}. "
333
- "Expected 'result'."
334
- )
335
- result = document.decode()
336
- filesystem_document = await client.read_block_document(
337
- result.filesystem_document_id
338
- )
339
- filesystem = Block._from_block_document(filesystem_document)
340
- return await filesystem.read_path(result.key)
341
-
342
-
343
- async def _retrieve_result(state, client):
344
- serialized_result = await _retrieve_serialized_result(state.data, client)
345
- return DataDocument.parse_raw(serialized_result).decode()
346
-
347
-
348
- class _Result(pydantic.BaseModel):
349
- key: str
350
- filesystem_document_id: uuid.UUID
@@ -1,12 +0,0 @@
1
- """
2
- DEPRECATION WARNING:
3
- This module is deprecated as of March 2024 and will not be available after September 2024.
4
- """
5
- from prefect.deprecated.packaging.docker import DockerPackager
6
- from prefect.deprecated.packaging.file import FilePackager
7
- from prefect.deprecated.packaging.orion import OrionPackager
8
-
9
- # isort: split
10
-
11
- # Register any packaging serializers
12
- import prefect.deprecated.packaging.serializers
@@ -1,96 +0,0 @@
1
- """
2
- DEPRECATION WARNING:
3
- This module is deprecated as of March 2024 and will not be available after September 2024.
4
- """
5
-
6
- import abc
7
- from typing import Generic, Type, TypeVar
8
-
9
- from prefect._internal.compatibility.deprecated import deprecated_class
10
- from prefect._internal.pydantic import HAS_PYDANTIC_V2
11
-
12
- if HAS_PYDANTIC_V2:
13
- from pydantic.v1 import BaseModel
14
- else:
15
- from pydantic import BaseModel
16
-
17
- from prefect.flows import Flow
18
- from prefect.utilities.callables import ParameterSchema, parameter_schema
19
- from prefect.utilities.dispatch import lookup_type
20
- from prefect.utilities.pydantic import add_type_dispatch
21
-
22
- D = TypeVar("D")
23
-
24
-
25
- @deprecated_class(start_date="Mar 2024")
26
- @add_type_dispatch
27
- class Serializer(BaseModel, Generic[D], abc.ABC):
28
- """
29
- DEPRECATION WARNING:
30
-
31
- This class is deprecated as of version March 2024 and will not be available after September 2024.
32
-
33
- A serializer that can encode objects of type 'D' into bytes.
34
- """
35
-
36
- type: str
37
-
38
- def dumps(self, obj: D) -> bytes:
39
- """Encode the object into a blob of bytes."""
40
-
41
- def loads(self, blob: bytes) -> D:
42
- """Decode the blob of bytes into an object."""
43
-
44
-
45
- @deprecated_class(start_date="Mar 2024")
46
- @add_type_dispatch
47
- class PackageManifest(BaseModel, abc.ABC):
48
- """
49
- DEPRECATION WARNING:
50
-
51
- This class is deprecated as of version March 2024 and will not be available after September 2024.
52
-
53
- Describes a package.
54
- """
55
-
56
- type: str
57
- flow_name: str
58
- flow_parameter_schema: ParameterSchema
59
-
60
- @abc.abstractmethod
61
- async def unpackage(self) -> Flow:
62
- """
63
- Retrieve a flow from the package.
64
- """
65
-
66
-
67
- @deprecated_class(start_date="Mar 2024")
68
- @add_type_dispatch
69
- class Packager(BaseModel, abc.ABC):
70
- """
71
- DEPRECATION WARNING:
72
-
73
- This class is deprecated as of version March 2024 and will not be available after September 2024.
74
-
75
- Creates a package for a flow.
76
-
77
- A package contains the flow and is typically stored outside of Prefect. To
78
- facilitate interaction with the package, a manifest is returned that describes how
79
- to access and use the package.
80
- """
81
-
82
- type: str
83
-
84
- def base_manifest(self, flow: Flow) -> PackageManifest:
85
- manifest_cls: Type[BaseModel] = lookup_type(PackageManifest, self.type)
86
- return manifest_cls.construct(
87
- type=self.type,
88
- flow_name=flow.name,
89
- flow_parameter_schema=parameter_schema(flow.fn),
90
- )
91
-
92
- @abc.abstractmethod
93
- async def package(self, flow: Flow) -> "PackageManifest":
94
- """
95
- Package a flow and return a manifest describing the created package.
96
- """
@@ -1,146 +0,0 @@
1
- """
2
- DEPRECATION WARNING:
3
- This module is deprecated as of March 2024 and will not be available after September 2024.
4
- """
5
-
6
- import json
7
- import sys
8
- from pathlib import Path
9
- from typing import Any, Mapping, Optional, Union
10
-
11
- from prefect._internal.compatibility.deprecated import deprecated_class
12
- from prefect._internal.pydantic import HAS_PYDANTIC_V2
13
- from prefect._internal.schemas.validators import (
14
- assign_default_base_image,
15
- base_image_xor_dockerfile,
16
- set_default_python_environment,
17
- validate_registry_url,
18
- )
19
-
20
- if HAS_PYDANTIC_V2:
21
- from pydantic.v1 import AnyHttpUrl, root_validator, validator
22
- else:
23
- from pydantic import AnyHttpUrl, root_validator, validator
24
- from typing_extensions import Literal
25
-
26
- from prefect.deprecated.packaging.base import PackageManifest, Packager
27
- from prefect.deprecated.packaging.serializers import SourceSerializer
28
- from prefect.flows import Flow, load_flow_from_script
29
- from prefect.software import CondaEnvironment, PythonEnvironment
30
- from prefect.utilities.asyncutils import run_sync_in_worker_thread
31
- from prefect.utilities.dockerutils import (
32
- ImageBuilder,
33
- build_image,
34
- push_image,
35
- to_run_command,
36
- )
37
- from prefect.utilities.slugify import slugify
38
-
39
-
40
- @deprecated_class(start_date="Mar 2024")
41
- class DockerPackageManifest(PackageManifest):
42
- """
43
- DEPRECATION WARNING:
44
-
45
- This class is deprecated as of version March 2024 and will not be available after September 2024.
46
-
47
- Represents a flow packaged in a Docker image
48
- """
49
-
50
- type: Literal["docker"] = "docker"
51
-
52
- image: str
53
- image_flow_location: str
54
-
55
- async def unpackage(self) -> Flow:
56
- return load_flow_from_script(self.image_flow_location, self.flow_name)
57
-
58
-
59
- @deprecated_class(start_date="Mar 2024")
60
- class DockerPackager(Packager):
61
- """
62
- DEPRECATION WARNING:
63
-
64
- This class is deprecated as of version March 2024 and will not be available after September 2024.
65
-
66
- This packager builds a Docker image containing the flow and the runtime environment
67
- necessary to run the flow. The resulting image is optionally pushed to a container
68
- registry, given by `registry_url`.
69
- """
70
-
71
- type: str = "docker"
72
-
73
- base_image: Optional[str] = None
74
- python_environment: Optional[Union[PythonEnvironment, CondaEnvironment]] = None
75
- dockerfile: Optional[Path] = None
76
- platform: Optional[str] = (None,)
77
- image_flow_location: str = "/flow.py"
78
- registry_url: Optional[AnyHttpUrl] = None
79
-
80
- @root_validator
81
- def set_default_base_image(cls, values):
82
- return assign_default_base_image(values)
83
-
84
- @root_validator
85
- def base_image_and_dockerfile_exclusive(cls, values: Mapping[str, Any]):
86
- return base_image_xor_dockerfile(values)
87
-
88
- @root_validator
89
- def default_python_environment(cls, values: Mapping[str, Any]):
90
- return set_default_python_environment(values)
91
-
92
- @validator("registry_url", pre=True)
93
- def ensure_registry_url_is_prefixed(cls, value):
94
- validate_registry_url(value)
95
-
96
- async def package(self, flow: Flow) -> DockerPackageManifest:
97
- """
98
- Package a flow as a Docker image and, optionally, push it to a registry
99
- """
100
- image_reference = await self._build_image(flow)
101
-
102
- if self.registry_url:
103
- image_name = f"{slugify(flow.name)}"
104
- image_reference = await run_sync_in_worker_thread(
105
- push_image, image_reference, self.registry_url, image_name
106
- )
107
-
108
- return DockerPackageManifest(
109
- **{
110
- **self.base_manifest(flow).dict(),
111
- **{
112
- "image": image_reference,
113
- "image_flow_location": self.image_flow_location,
114
- },
115
- }
116
- )
117
-
118
- async def _build_image(self, flow: Flow) -> str:
119
- if self.dockerfile:
120
- return await self._build_from_dockerfile()
121
- return await self._build_from_base_image(flow)
122
-
123
- async def _build_from_dockerfile(self) -> str:
124
- context = self.dockerfile.resolve().parent
125
- dockerfile = self.dockerfile.relative_to(context)
126
- return await run_sync_in_worker_thread(
127
- build_image,
128
- platform=self.platform,
129
- context=context,
130
- dockerfile=str(dockerfile),
131
- )
132
-
133
- async def _build_from_base_image(self, flow: Flow) -> str:
134
- with ImageBuilder(
135
- base_image=self.base_image, platform=self.platform
136
- ) as builder:
137
- for command in self.python_environment.install_commands():
138
- builder.add_line(to_run_command(command))
139
-
140
- source_info = json.loads(SourceSerializer().dumps(flow))
141
-
142
- builder.write_text(source_info["source"], self.image_flow_location)
143
-
144
- return await run_sync_in_worker_thread(
145
- builder.build, stream_progress_to=sys.stdout
146
- )
@@ -1,92 +0,0 @@
1
- """
2
- DEPRECATION WARNING:
3
- This module is deprecated as of March 2024 and will not be available after September 2024.
4
- """
5
-
6
- from uuid import UUID
7
-
8
- from prefect._internal.compatibility.deprecated import deprecated_class
9
- from prefect._internal.pydantic import HAS_PYDANTIC_V2
10
-
11
- if HAS_PYDANTIC_V2:
12
- from pydantic.v1 import Field
13
- else:
14
- from pydantic import Field
15
-
16
- from typing_extensions import Literal
17
-
18
- from prefect.blocks.core import Block
19
- from prefect.client.orchestration import PrefectClient
20
- from prefect.client.utilities import inject_client
21
- from prefect.deprecated.packaging.base import PackageManifest, Packager, Serializer
22
- from prefect.deprecated.packaging.serializers import SourceSerializer
23
- from prefect.filesystems import LocalFileSystem, ReadableFileSystem, WritableFileSystem
24
- from prefect.flows import Flow
25
- from prefect.settings import PREFECT_HOME
26
- from prefect.utilities.hashing import stable_hash
27
-
28
-
29
- @deprecated_class(start_date="Mar 2024")
30
- class FilePackageManifest(PackageManifest):
31
- """
32
- DEPRECATION WARNING:
33
-
34
- This class is deprecated as of version March 2024 and will not be available after September 2024.
35
- """
36
-
37
- type: str = "file"
38
- serializer: Serializer
39
- key: str
40
- filesystem_id: UUID
41
-
42
- @inject_client
43
- async def unpackage(self, client: PrefectClient) -> Flow:
44
- block_document = await client.read_block_document(self.filesystem_id)
45
- filesystem: ReadableFileSystem = Block._from_block_document(block_document)
46
- content = await filesystem.read_path(self.key)
47
- return self.serializer.loads(content)
48
-
49
-
50
- @deprecated_class(start_date="Mar 2024")
51
- class FilePackager(Packager):
52
- """
53
- DEPRECATION WARNING:
54
-
55
- This class is deprecated as of version March 2024 and will not be available after September 2024.
56
-
57
- This packager stores the flow as a single file.
58
-
59
- By default, the file is the source code of the module the flow is defined in.
60
- Alternative serialization modes are available in `prefect.deprecated.packaging.serializers`.
61
- """
62
-
63
- type: Literal["file"] = "file"
64
- serializer: Serializer = Field(default_factory=SourceSerializer)
65
- filesystem: WritableFileSystem = Field(
66
- default_factory=lambda: LocalFileSystem(
67
- basepath=PREFECT_HOME.value() / "storage"
68
- )
69
- )
70
-
71
- @inject_client
72
- async def package(self, flow: Flow, client: "PrefectClient") -> FilePackageManifest:
73
- content = self.serializer.dumps(flow)
74
- key = stable_hash(content)
75
-
76
- await self.filesystem.write_path(key, content)
77
-
78
- filesystem_id = (
79
- self.filesystem._block_document_id
80
- or await self.filesystem._save(is_anonymous=True)
81
- )
82
-
83
- return FilePackageManifest(
84
- **{
85
- **self.base_manifest(flow).dict(),
86
- **{
87
- "serializer": self.serializer,
88
- "filesystem_id": filesystem_id,
89
- "key": key,
90
- },
91
- }
92
- )