wmill 1.253.4__py3-none-any.whl → 1.253.8__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.

Potentially problematic release.


This version of wmill might be problematic. Click here for more details.

wmill/client.py CHANGED
@@ -3,6 +3,7 @@ from __future__ import annotations
3
3
  import atexit
4
4
  import datetime as dt
5
5
  import functools
6
+ from io import BufferedReader, BytesIO
6
7
  import logging
7
8
  import os
8
9
  import random
@@ -395,7 +396,7 @@ class Windmill:
395
396
  part_response = self.post(
396
397
  f"/w/{self.workspace}/job_helpers/multipart_download_s3_file",
397
398
  json={
398
- "file_key": s3object.s3,
399
+ "file_key": s3object["s3"],
399
400
  "part_number": part_number,
400
401
  "file_size": file_total_size,
401
402
  "s3_resource_path": s3_resource_path,
@@ -413,7 +414,7 @@ class Windmill:
413
414
  def write_s3_file(
414
415
  self,
415
416
  s3object: S3Object | None,
416
- file_content: bytes,
417
+ file_content: BufferedReader | bytes,
417
418
  file_expiration: dt.datetime | None,
418
419
  s3_resource_path: str | None,
419
420
  ) -> S3Object:
@@ -424,26 +425,56 @@ class Windmill:
424
425
  from wmill import S3Object
425
426
 
426
427
  s3_obj = S3Object(s3="/path/to/my_file.txt")
428
+
429
+ # for an in memory bytes array:
427
430
  file_content = b'Hello Windmill!'
428
431
  client.write_s3_file(s3_obj, file_content)
432
+
433
+ # for a file:
434
+ with open("my_file.txt", "rb") as my_file:
435
+ client.write_s3_file(s3_obj, my_file)
429
436
  '''
430
437
  """
431
- try:
432
- result = self.post(
433
- f"/w/{self.workspace}/job_helpers/multipart_upload_s3_file",
434
- json={
435
- "file_key": s3object.s3 if s3object is not None else None,
436
- "part_content": file_content,
437
- "parts": [],
438
- "is_final": True,
439
- "cancel_upload": False,
440
- "s3_resource_path": s3_resource_path if s3_resource_path != "" else None,
441
- "file_expiration": file_expiration.isoformat() if file_expiration else None,
442
- },
443
- ).json()
444
- except Exception as e:
445
- raise Exception("Could not write file to S3") from e
446
- return S3Object(s3=result["file_key"])
438
+ content_reader: BufferedReader | BytesIO
439
+ if isinstance(file_content, BufferedReader):
440
+ content_reader = file_content
441
+ elif isinstance(file_content, bytes):
442
+ content_reader = BytesIO(file_content)
443
+ else:
444
+ raise Exception("Type of file_content not supported")
445
+
446
+ file_key = s3object["s3"] if s3object is not None else None
447
+ parts = []
448
+ upload_id = None
449
+ chunk = content_reader.read(5 * 1024 * 1024)
450
+ if len(chunk) == 0:
451
+ raise Exception("File content is empty, nothing to upload")
452
+ while True:
453
+ chunk_2 = content_reader.read(5 * 1024 * 1024)
454
+ reader_done = len(chunk_2) == 0
455
+ try:
456
+ response = self.post(
457
+ f"/w/{self.workspace}/job_helpers/multipart_upload_s3_file",
458
+ json={
459
+ "file_key": file_key,
460
+ "part_content": [b for b in chunk],
461
+ "upload_id": upload_id,
462
+ "parts": parts,
463
+ "is_final": reader_done,
464
+ "cancel_upload": False,
465
+ "s3_resource_path": s3_resource_path,
466
+ "file_expiration": file_expiration.isoformat() if file_expiration else None,
467
+ },
468
+ ).json()
469
+ except Exception as e:
470
+ raise Exception("Could not write file to S3") from e
471
+ parts = response["parts"]
472
+ upload_id = response["upload_id"]
473
+ file_key = response["file_key"]
474
+ if response["is_done"]:
475
+ break
476
+ chunk = chunk_2
477
+ return S3Object(s3=file_key)
447
478
 
448
479
  def __boto3_connection_settings(self, s3_resource) -> Boto3ConnectionSettings:
449
480
  endpoint_url_prefix = "https://" if s3_resource["useSSL"] else "http://"
@@ -706,8 +737,8 @@ def load_s3_file(s3object: S3Object, s3_resource_path: str = "") -> bytes:
706
737
  @init_global_client
707
738
  def write_s3_file(
708
739
  s3object: S3Object | None,
709
- file_content: bytes,
710
- file_expiration: dt.datetime | None,
740
+ file_content: BufferedReader | bytes,
741
+ file_expiration: dt.datetime | None = None,
711
742
  s3_resource_path: str = "",
712
743
  ) -> S3Object:
713
744
  """
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: wmill
3
- Version: 1.253.4
3
+ Version: 1.253.8
4
4
  Summary: A client library for accessing Windmill server wrapping the Windmill client API
5
5
  Home-page: https://windmill.dev
6
6
  License: Apache-2.0
@@ -0,0 +1,7 @@
1
+ wmill/__init__.py,sha256=nGZnQPezTdrBnBW1D0JqUtm75Gdf_xi3tAcPGwHRZ5A,46
2
+ wmill/client.py,sha256=sYT8hTPj9w0_-BysAU-XHBvQyW98KgI5p_X4PTIjxDE,27732
3
+ wmill/py.typed,sha256=8PjyZ1aVoQpRVvt71muvuq5qE-jTFZkK-GLHkhdebmc,26
4
+ wmill/s3_types.py,sha256=axVibTMtpynBwaCVK0O6bBao56no01qflyIGRaVyV6s,1149
5
+ wmill-1.253.8.dist-info/METADATA,sha256=ewkNYazeaKSuwJ5Swcanxi6ekjru6EI3cpr2EtvdgWY,2699
6
+ wmill-1.253.8.dist-info/WHEEL,sha256=d2fvjOD7sXsVzChCqf0Ty0JbHKBaLYwDbGQDwQTnJ50,88
7
+ wmill-1.253.8.dist-info/RECORD,,
@@ -1,7 +0,0 @@
1
- wmill/__init__.py,sha256=nGZnQPezTdrBnBW1D0JqUtm75Gdf_xi3tAcPGwHRZ5A,46
2
- wmill/client.py,sha256=feV_L0u1q09O44Zv4YtbdYjOCpVuk36jx45n3rz62no,26517
3
- wmill/py.typed,sha256=8PjyZ1aVoQpRVvt71muvuq5qE-jTFZkK-GLHkhdebmc,26
4
- wmill/s3_types.py,sha256=axVibTMtpynBwaCVK0O6bBao56no01qflyIGRaVyV6s,1149
5
- wmill-1.253.4.dist-info/METADATA,sha256=y-nQn2KXOFn-As5orCrCy0YLm8CfChuh32xSRcAhtA4,2699
6
- wmill-1.253.4.dist-info/WHEEL,sha256=d2fvjOD7sXsVzChCqf0Ty0JbHKBaLYwDbGQDwQTnJ50,88
7
- wmill-1.253.4.dist-info/RECORD,,