airbyte-cdk 6.30.0__py3-none-any.whl → 6.31.0__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.
@@ -482,16 +482,16 @@ class AsyncJobOrchestrator:
482
482
  and exception.failure_type == FailureType.config_error
483
483
  )
484
484
 
485
- def fetch_records(self, partition: AsyncPartition) -> Iterable[Mapping[str, Any]]:
485
+ def fetch_records(self, async_jobs: Iterable[AsyncJob]) -> Iterable[Mapping[str, Any]]:
486
486
  """
487
- Fetches records from the given partition's jobs.
487
+ Fetches records from the given jobs.
488
488
 
489
489
  Args:
490
- partition (AsyncPartition): The partition containing the jobs.
490
+ async_jobs Iterable[AsyncJob]: The list of AsyncJobs.
491
491
 
492
492
  Yields:
493
493
  Iterable[Mapping[str, Any]]: The fetched records from the jobs.
494
494
  """
495
- for job in partition.jobs:
495
+ for job in async_jobs:
496
496
  yield from self._job_repository.fetch_records(job)
497
497
  self._job_repository.delete(job)
@@ -19,6 +19,7 @@ from airbyte_cdk.sources.declarative.extractors import RecordSelector
19
19
  from airbyte_cdk.sources.declarative.extractors.record_filter import (
20
20
  ClientSideIncrementalRecordFilterDecorator,
21
21
  )
22
+ from airbyte_cdk.sources.declarative.incremental import ConcurrentPerPartitionCursor
22
23
  from airbyte_cdk.sources.declarative.incremental.datetime_based_cursor import DatetimeBasedCursor
23
24
  from airbyte_cdk.sources.declarative.incremental.per_partition_with_global import (
24
25
  PerPartitionWithGlobalCursor,
@@ -231,7 +232,7 @@ class ConcurrentDeclarativeSource(ManifestDeclarativeSource, Generic[TState]):
231
232
  ):
232
233
  cursor = declarative_stream.retriever.stream_slicer.stream_slicer
233
234
 
234
- if not isinstance(cursor, ConcurrentCursor):
235
+ if not isinstance(cursor, ConcurrentCursor | ConcurrentPerPartitionCursor):
235
236
  # This should never happen since we instantiate ConcurrentCursor in
236
237
  # model_to_component_factory.py
237
238
  raise ValueError(
@@ -138,7 +138,9 @@ class DeclarativeStream(Stream):
138
138
  """
139
139
  :param: stream_state We knowingly avoid using stream_state as we want cursors to manage their own state.
140
140
  """
141
- if stream_slice is None or stream_slice == {}:
141
+ if stream_slice is None or (
142
+ not isinstance(stream_slice, StreamSlice) and stream_slice == {}
143
+ ):
142
144
  # As the parameter is Optional, many would just call `read_records(sync_mode)` during testing without specifying the field
143
145
  # As part of the declarative model without custom components, this should never happen as the CDK would wire up a
144
146
  # SinglePartitionRouter that would create this StreamSlice properly
@@ -1656,7 +1656,7 @@ class ModelToComponentFactory:
1656
1656
  ) -> Optional[PartitionRouter]:
1657
1657
  if (
1658
1658
  hasattr(model, "partition_router")
1659
- and isinstance(model, SimpleRetrieverModel)
1659
+ and isinstance(model, SimpleRetrieverModel | AsyncRetrieverModel)
1660
1660
  and model.partition_router
1661
1661
  ):
1662
1662
  stream_slicer_model = model.partition_router
@@ -1690,6 +1690,31 @@ class ModelToComponentFactory:
1690
1690
  stream_slicer = self._build_stream_slicer_from_partition_router(model.retriever, config)
1691
1691
 
1692
1692
  if model.incremental_sync and stream_slicer:
1693
+ if model.retriever.type == "AsyncRetriever":
1694
+ if model.incremental_sync.type != "DatetimeBasedCursor":
1695
+ # We are currently in a transition to the Concurrent CDK and AsyncRetriever can only work with the support or unordered slices (for example, when we trigger reports for January and February, the report in February can be completed first). Once we have support for custom concurrent cursor or have a new implementation available in the CDK, we can enable more cursors here.
1696
+ raise ValueError(
1697
+ "AsyncRetriever with cursor other than DatetimeBasedCursor is not supported yet"
1698
+ )
1699
+ if stream_slicer:
1700
+ return self.create_concurrent_cursor_from_perpartition_cursor( # type: ignore # This is a known issue that we are creating and returning a ConcurrentCursor which does not technically implement the (low-code) StreamSlicer. However, (low-code) StreamSlicer and ConcurrentCursor both implement StreamSlicer.stream_slices() which is the primary method needed for checkpointing
1701
+ state_manager=self._connector_state_manager,
1702
+ model_type=DatetimeBasedCursorModel,
1703
+ component_definition=model.incremental_sync.__dict__,
1704
+ stream_name=model.name or "",
1705
+ stream_namespace=None,
1706
+ config=config or {},
1707
+ stream_state={},
1708
+ partition_router=stream_slicer,
1709
+ )
1710
+ return self.create_concurrent_cursor_from_datetime_based_cursor( # type: ignore # This is a known issue that we are creating and returning a ConcurrentCursor which does not technically implement the (low-code) StreamSlicer. However, (low-code) StreamSlicer and ConcurrentCursor both implement StreamSlicer.stream_slices() which is the primary method needed for checkpointing
1711
+ model_type=DatetimeBasedCursorModel,
1712
+ component_definition=model.incremental_sync.__dict__,
1713
+ stream_name=model.name or "",
1714
+ stream_namespace=None,
1715
+ config=config or {},
1716
+ )
1717
+
1693
1718
  incremental_sync_model = model.incremental_sync
1694
1719
  if (
1695
1720
  hasattr(incremental_sync_model, "global_substream_cursor")
@@ -4,9 +4,9 @@ from dataclasses import InitVar, dataclass, field
4
4
  from typing import Any, Callable, Iterable, Mapping, Optional
5
5
 
6
6
  from airbyte_cdk.models import FailureType
7
+ from airbyte_cdk.sources.declarative.async_job.job import AsyncJob
7
8
  from airbyte_cdk.sources.declarative.async_job.job_orchestrator import (
8
9
  AsyncJobOrchestrator,
9
- AsyncPartition,
10
10
  )
11
11
  from airbyte_cdk.sources.declarative.partition_routers.single_partition_router import (
12
12
  SinglePartitionRouter,
@@ -42,12 +42,12 @@ class AsyncJobPartitionRouter(StreamSlicer):
42
42
 
43
43
  for completed_partition in self._job_orchestrator.create_and_get_completed_partitions():
44
44
  yield StreamSlice(
45
- partition=dict(completed_partition.stream_slice.partition)
46
- | {"partition": completed_partition},
45
+ partition=dict(completed_partition.stream_slice.partition),
47
46
  cursor_slice=completed_partition.stream_slice.cursor_slice,
47
+ extra_fields={"jobs": list(completed_partition.jobs)},
48
48
  )
49
49
 
50
- def fetch_records(self, partition: AsyncPartition) -> Iterable[Mapping[str, Any]]:
50
+ def fetch_records(self, async_jobs: Iterable[AsyncJob]) -> Iterable[Mapping[str, Any]]:
51
51
  """
52
52
  This method of fetching records extends beyond what a PartitionRouter/StreamSlicer should
53
53
  be responsible for. However, this was added in because the JobOrchestrator is required to
@@ -62,4 +62,4 @@ class AsyncJobPartitionRouter(StreamSlicer):
62
62
  failure_type=FailureType.system_error,
63
63
  )
64
64
 
65
- return self._job_orchestrator.fetch_records(partition=partition)
65
+ return self._job_orchestrator.fetch_records(async_jobs=async_jobs)
@@ -6,7 +6,7 @@ from typing import Any, Iterable, Mapping, Optional
6
6
 
7
7
  from typing_extensions import deprecated
8
8
 
9
- from airbyte_cdk.models import FailureType
9
+ from airbyte_cdk.sources.declarative.async_job.job import AsyncJob
10
10
  from airbyte_cdk.sources.declarative.async_job.job_orchestrator import AsyncPartition
11
11
  from airbyte_cdk.sources.declarative.extractors.record_selector import RecordSelector
12
12
  from airbyte_cdk.sources.declarative.partition_routers.async_job_partition_router import (
@@ -16,7 +16,6 @@ from airbyte_cdk.sources.declarative.retrievers.retriever import Retriever
16
16
  from airbyte_cdk.sources.source import ExperimentalClassWarning
17
17
  from airbyte_cdk.sources.streams.core import StreamData
18
18
  from airbyte_cdk.sources.types import Config, StreamSlice, StreamState
19
- from airbyte_cdk.utils.traced_exception import AirbyteTracedException
20
19
 
21
20
 
22
21
  @deprecated(
@@ -57,9 +56,9 @@ class AsyncRetriever(Retriever):
57
56
 
58
57
  return self.state
59
58
 
60
- def _validate_and_get_stream_slice_partition(
59
+ def _validate_and_get_stream_slice_jobs(
61
60
  self, stream_slice: Optional[StreamSlice] = None
62
- ) -> AsyncPartition:
61
+ ) -> Iterable[AsyncJob]:
63
62
  """
64
63
  Validates the stream_slice argument and returns the partition from it.
65
64
 
@@ -73,12 +72,7 @@ class AsyncRetriever(Retriever):
73
72
  AirbyteTracedException: If the stream_slice is not an instance of StreamSlice or if the partition is not present in the stream_slice.
74
73
 
75
74
  """
76
- if not isinstance(stream_slice, StreamSlice) or "partition" not in stream_slice.partition:
77
- raise AirbyteTracedException(
78
- message="Invalid arguments to AsyncRetriever.read_records: stream_slice is not optional. Please contact Airbyte Support",
79
- failure_type=FailureType.system_error,
80
- )
81
- return stream_slice["partition"] # type: ignore # stream_slice["partition"] has been added as an AsyncPartition as part of stream_slices
75
+ return stream_slice.extra_fields.get("jobs", []) if stream_slice else []
82
76
 
83
77
  def stream_slices(self) -> Iterable[Optional[StreamSlice]]:
84
78
  return self.stream_slicer.stream_slices()
@@ -89,8 +83,8 @@ class AsyncRetriever(Retriever):
89
83
  stream_slice: Optional[StreamSlice] = None,
90
84
  ) -> Iterable[StreamData]:
91
85
  stream_state: StreamState = self._get_stream_state()
92
- partition: AsyncPartition = self._validate_and_get_stream_slice_partition(stream_slice)
93
- records: Iterable[Mapping[str, Any]] = self.stream_slicer.fetch_records(partition)
86
+ jobs: Iterable[AsyncJob] = self._validate_and_get_stream_slice_jobs(stream_slice)
87
+ records: Iterable[Mapping[str, Any]] = self.stream_slicer.fetch_records(jobs)
94
88
 
95
89
  yield from self.record_selector.filter_and_transform(
96
90
  all_data=records,
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: airbyte-cdk
3
- Version: 6.30.0
3
+ Version: 6.31.0
4
4
  Summary: A framework for writing Airbyte Connectors.
5
5
  Home-page: https://airbyte.com
6
6
  License: MIT
@@ -45,7 +45,7 @@ airbyte_cdk/sources/connector_state_manager.py,sha256=hw3TJJWl3UJKSDsH-PypFQU7mD
45
45
  airbyte_cdk/sources/declarative/__init__.py,sha256=ZnqYNxHsKCgO38IwB34RQyRMXTs4GTvlRi3ImKnIioo,61
46
46
  airbyte_cdk/sources/declarative/async_job/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
47
47
  airbyte_cdk/sources/declarative/async_job/job.py,sha256=V4Z6NohXwTlOavDbD-tUUQxOr7Lzpb_r4tRC64AfvDE,1702
48
- airbyte_cdk/sources/declarative/async_job/job_orchestrator.py,sha256=pxGYT933i5GbhbtrIT5aw3TbiRqv2TVyZ0O02X0mM8c,21021
48
+ airbyte_cdk/sources/declarative/async_job/job_orchestrator.py,sha256=F-NH7PMLvACKhzEESEv6tDai_gYT8HzGncoqG5991l8,21001
49
49
  airbyte_cdk/sources/declarative/async_job/job_tracker.py,sha256=SQt21SftVgP7RUCQ8LA2vaCn-YEbyX1BnhibfTX9oaE,2321
50
50
  airbyte_cdk/sources/declarative/async_job/repository.py,sha256=2OkWiZp5IKTOi_SIpP1U-Rw3gH36LBy_a8CgXoENTtg,1044
51
51
  airbyte_cdk/sources/declarative/async_job/status.py,sha256=mkExR-uOAO1ckUnclaUOa74l2N9CdhLbVFM6KDoBgBM,715
@@ -63,13 +63,13 @@ airbyte_cdk/sources/declarative/checks/check_stream.py,sha256=dAA-UhmMj0WLXCkRQr
63
63
  airbyte_cdk/sources/declarative/checks/connection_checker.py,sha256=MBRJo6WJlZQHpIfOGaNOkkHUmgUl_4wDM6VPo41z5Ss,1383
64
64
  airbyte_cdk/sources/declarative/concurrency_level/__init__.py,sha256=5XUqrmlstYlMM0j6crktlKQwALek0uiz2D3WdM46MyA,191
65
65
  airbyte_cdk/sources/declarative/concurrency_level/concurrency_level.py,sha256=YIwCTCpOr_QSNW4ltQK0yUGWInI8PKNY216HOOegYLk,2101
66
- airbyte_cdk/sources/declarative/concurrent_declarative_source.py,sha256=uhSXYhXD56E-Wr9qRqzgLmIW1sFHj_2sIXk0enOtpms,27305
66
+ airbyte_cdk/sources/declarative/concurrent_declarative_source.py,sha256=x5a_Wv0chLAo2knBg-yQZoo5zUyfDsOuF4tEz3oHehc,27421
67
67
  airbyte_cdk/sources/declarative/datetime/__init__.py,sha256=l9LG7Qm6e5r_qgqfVKnx3mXYtg1I9MmMjomVIPfU4XA,177
68
68
  airbyte_cdk/sources/declarative/datetime/datetime_parser.py,sha256=SX9JjdesN1edN2WVUVMzU_ptqp2QB1OnsnjZ4mwcX7w,2579
69
69
  airbyte_cdk/sources/declarative/datetime/min_max_datetime.py,sha256=0BHBtDNQZfvwM45-tY5pNlTcKAFSGGNxemoi0Jic-0E,5785
70
70
  airbyte_cdk/sources/declarative/declarative_component_schema.yaml,sha256=43cBrshQer-KiNwjlA6peDyfrST88VQIZmfgdAZTiLc,139874
71
71
  airbyte_cdk/sources/declarative/declarative_source.py,sha256=nF7wBqFd3AQmEKAm4CnIo29CJoQL562cJGSCeL8U8bA,1531
72
- airbyte_cdk/sources/declarative/declarative_stream.py,sha256=JRyNeOIpsFu4ztVZsN6sncqUEIqIE-bUkD2TPgbMgk0,10375
72
+ airbyte_cdk/sources/declarative/declarative_stream.py,sha256=venZjfpvtqr3oFSuvMBWtn4h9ayLhD4L65ACuXCDZ64,10445
73
73
  airbyte_cdk/sources/declarative/decoders/__init__.py,sha256=KSpQetKGqPCv-38QgcVJ5kzM5nzbFldTSsYDCS3Xf0Y,1035
74
74
  airbyte_cdk/sources/declarative/decoders/composite_raw_decoder.py,sha256=kQfUVMVhChKe5OngwIQrs0F9KGnRUN-CKVFakCU23DQ,4354
75
75
  airbyte_cdk/sources/declarative/decoders/decoder.py,sha256=sl-Gt8lXi7yD2Q-sD8je5QS2PbgrgsYjxRLWsay7DMc,826
@@ -115,9 +115,9 @@ airbyte_cdk/sources/declarative/parsers/custom_code_compiler.py,sha256=958MMX6_Z
115
115
  airbyte_cdk/sources/declarative/parsers/custom_exceptions.py,sha256=Rir9_z3Kcd5Es0-LChrzk-0qubAsiK_RSEnLmK2OXm8,553
116
116
  airbyte_cdk/sources/declarative/parsers/manifest_component_transformer.py,sha256=CXwTfD3wSQq3okcqwigpprbHhSURUokh4GK2OmOyKC8,9132
117
117
  airbyte_cdk/sources/declarative/parsers/manifest_reference_resolver.py,sha256=IWUOdF03o-aQn0Occo1BJCxU0Pz-QILk5L67nzw2thw,6803
118
- airbyte_cdk/sources/declarative/parsers/model_to_component_factory.py,sha256=RzJ4rA4Gb8IhfkSHki19JyDzy0ICf31mCnM0YAy7c8g,126270
118
+ airbyte_cdk/sources/declarative/parsers/model_to_component_factory.py,sha256=f8gzijhJtUEJqNZvZihaFyBqrn8xqxjYrncgiXeKZY8,128557
119
119
  airbyte_cdk/sources/declarative/partition_routers/__init__.py,sha256=HJ-Syp3p7RpyR_OK0X_a2kSyISfu3W-PKrRI16iY0a8,957
120
- airbyte_cdk/sources/declarative/partition_routers/async_job_partition_router.py,sha256=n82J15S8bjeMZ5uROu--P3hnbQoxkY5v7RPHYx7g7ro,2929
120
+ airbyte_cdk/sources/declarative/partition_routers/async_job_partition_router.py,sha256=VelO7zKqKtzMJ35jyFeg0ypJLQC0plqqIBNXoBW1G2E,3001
121
121
  airbyte_cdk/sources/declarative/partition_routers/cartesian_product_stream_slicer.py,sha256=c5cuVFM6NFkuQqG8Z5IwkBuwDrvXZN1CunUOM_L0ezg,6892
122
122
  airbyte_cdk/sources/declarative/partition_routers/list_partition_router.py,sha256=t7pRdFWfFWJtQQG19c9PVeMODyO2BknRTakpM5U9N-8,4844
123
123
  airbyte_cdk/sources/declarative/partition_routers/partition_router.py,sha256=YyEIzdmLd1FjbVP3QbQ2VFCLW_P-OGbVh6VpZShp54k,2218
@@ -165,7 +165,7 @@ airbyte_cdk/sources/declarative/resolvers/components_resolver.py,sha256=KPjKc0yb
165
165
  airbyte_cdk/sources/declarative/resolvers/config_components_resolver.py,sha256=dz4iJV9liD_LzY_Mn4XmAStoUll60R3MIGWV4aN3pgg,5223
166
166
  airbyte_cdk/sources/declarative/resolvers/http_components_resolver.py,sha256=AiojNs8wItJFrENZBFUaDvau3sgwudO6Wkra36upSPo,4639
167
167
  airbyte_cdk/sources/declarative/retrievers/__init__.py,sha256=ix9m1dkR69DcXCXUKC5RK_ZZM7ojTLBQ4IkWQTfmfCk,456
168
- airbyte_cdk/sources/declarative/retrievers/async_retriever.py,sha256=aIxZUhDgq1-fuWKkSrElHyuQaxLsKhbbZM6bWO_VFTQ,3694
168
+ airbyte_cdk/sources/declarative/retrievers/async_retriever.py,sha256=2oQn_vo7uJKp4pdMnsF5CG5Iwc9rkPeEOLoAm_9bcus,3222
169
169
  airbyte_cdk/sources/declarative/retrievers/retriever.py,sha256=XPLs593Xv8c5cKMc37XzUAYmzlXd1a7eSsspM-CMuWA,1696
170
170
  airbyte_cdk/sources/declarative/retrievers/simple_retriever.py,sha256=kgnhVQxRlFqJs2-rDu2-QH-p-GzQU3nKmSp6_aq8u0s,24550
171
171
  airbyte_cdk/sources/declarative/schema/__init__.py,sha256=xU45UvM5O4c1PSM13UHpCdh5hpW3HXy9vRRGEiAC1rg,795
@@ -351,9 +351,9 @@ airbyte_cdk/utils/slice_hasher.py,sha256=EDxgROHDbfG-QKQb59m7h_7crN1tRiawdf5uU7G
351
351
  airbyte_cdk/utils/spec_schema_transformations.py,sha256=-5HTuNsnDBAhj-oLeQXwpTGA0HdcjFOf2zTEMUTTg_Y,816
352
352
  airbyte_cdk/utils/stream_status_utils.py,sha256=ZmBoiy5HVbUEHAMrUONxZvxnvfV9CesmQJLDTAIWnWw,1171
353
353
  airbyte_cdk/utils/traced_exception.py,sha256=C8uIBuCL_E4WnBAOPSxBicD06JAldoN9fGsQDp463OY,6292
354
- airbyte_cdk-6.30.0.dist-info/LICENSE.txt,sha256=Wfe61S4BaGPj404v8lrAbvhjYR68SHlkzeYrg3_bbuM,1051
355
- airbyte_cdk-6.30.0.dist-info/LICENSE_SHORT,sha256=aqF6D1NcESmpn-cqsxBtszTEnHKnlsp8L4x9wAh3Nxg,55
356
- airbyte_cdk-6.30.0.dist-info/METADATA,sha256=2hcMctLdFzaw8Ta6E_SAreA3XoTx1uWvaeYGP8nfZgc,6010
357
- airbyte_cdk-6.30.0.dist-info/WHEEL,sha256=Nq82e9rUAnEjt98J6MlVmMCZb-t9cYE2Ir1kpBmnWfs,88
358
- airbyte_cdk-6.30.0.dist-info/entry_points.txt,sha256=fj-e3PAQvsxsQzyyq8UkG1k8spunWnD4BAH2AwlR6NM,95
359
- airbyte_cdk-6.30.0.dist-info/RECORD,,
354
+ airbyte_cdk-6.31.0.dist-info/LICENSE.txt,sha256=Wfe61S4BaGPj404v8lrAbvhjYR68SHlkzeYrg3_bbuM,1051
355
+ airbyte_cdk-6.31.0.dist-info/LICENSE_SHORT,sha256=aqF6D1NcESmpn-cqsxBtszTEnHKnlsp8L4x9wAh3Nxg,55
356
+ airbyte_cdk-6.31.0.dist-info/METADATA,sha256=KkfyPinQhIiUdGhAsYBhDd-cjf9YPVAfbGmZj3DVLo4,6010
357
+ airbyte_cdk-6.31.0.dist-info/WHEEL,sha256=Nq82e9rUAnEjt98J6MlVmMCZb-t9cYE2Ir1kpBmnWfs,88
358
+ airbyte_cdk-6.31.0.dist-info/entry_points.txt,sha256=fj-e3PAQvsxsQzyyq8UkG1k8spunWnD4BAH2AwlR6NM,95
359
+ airbyte_cdk-6.31.0.dist-info/RECORD,,