2626from datetime import datetime
2727from decimal import Decimal
2828from tempfile import NamedTemporaryFile
29- from typing import Any , Dict , Iterable , List , Optional , Sequence , Tuple , Union
29+ from typing import Any , Dict , Iterable , List , NewType , Optional , Sequence , Tuple , Union
3030from uuid import UUID
3131
3232from cassandra .util import Date , OrderedMapSerializedKey , SortedSet , Time
3636from airflow .providers .apache .cassandra .hooks .cassandra import CassandraHook
3737from airflow .providers .google .cloud .hooks .gcs import GCSHook
3838
39+ NotSetType = NewType ('NotSetType' , object )
40+ NOT_SET = NotSetType (object ())
41+
3942
4043class CassandraToGCSOperator (BaseOperator ):
4144 """
@@ -84,6 +87,10 @@ class CassandraToGCSOperator(BaseOperator):
8487 Service Account Token Creator IAM role to the directly preceding identity, with first
8588 account from the list granting this role to the originating account (templated).
8689 :type impersonation_chain: Union[str, Sequence[str]]
90+ :param query_timeout: (Optional) The amount of time, in seconds, used to execute the Cassandra query.
91+ If not set, the timeout value will be set in Session.execute() by Cassandra driver.
92+ If set to None, there is no timeout.
93+ :type query_timeout: float | None
8794 """
8895
8996 template_fields = (
@@ -110,6 +117,7 @@ def __init__(
110117 google_cloud_storage_conn_id : Optional [str ] = None ,
111118 delegate_to : Optional [str ] = None ,
112119 impersonation_chain : Optional [Union [str , Sequence [str ]]] = None ,
120+ query_timeout : Union [float , None , NotSetType ] = NOT_SET ,
113121 ** kwargs ,
114122 ) -> None :
115123 super ().__init__ (** kwargs )
@@ -133,6 +141,7 @@ def __init__(
133141 self .delegate_to = delegate_to
134142 self .gzip = gzip
135143 self .impersonation_chain = impersonation_chain
144+ self .query_timeout = query_timeout
136145
137146 # Default Cassandra to BigQuery type mapping
138147 CQL_TYPE_MAP = {
@@ -162,7 +171,12 @@ def __init__(
162171
163172 def execute (self , context : Dict [str , str ]):
164173 hook = CassandraHook (cassandra_conn_id = self .cassandra_conn_id )
165- cursor = hook .get_conn ().execute (self .cql )
174+
175+ query_extra = {}
176+ if self .query_timeout is not NOT_SET :
177+ query_extra ['timeout' ] = self .query_timeout
178+
179+ cursor = hook .get_conn ().execute (self .cql , ** query_extra )
166180
167181 files_to_upload = self ._write_local_data_files (cursor )
168182
0 commit comments