airbyte-agent-airtable 0.1.5__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 airbyte-agent-airtable might be problematic. Click here for more details.

Files changed (58) hide show
  1. airbyte_agent_airtable/__init__.py +81 -0
  2. airbyte_agent_airtable/_vendored/__init__.py +1 -0
  3. airbyte_agent_airtable/_vendored/connector_sdk/__init__.py +82 -0
  4. airbyte_agent_airtable/_vendored/connector_sdk/auth_strategies.py +1171 -0
  5. airbyte_agent_airtable/_vendored/connector_sdk/auth_template.py +135 -0
  6. airbyte_agent_airtable/_vendored/connector_sdk/cloud_utils/__init__.py +5 -0
  7. airbyte_agent_airtable/_vendored/connector_sdk/cloud_utils/client.py +338 -0
  8. airbyte_agent_airtable/_vendored/connector_sdk/connector_model_loader.py +1121 -0
  9. airbyte_agent_airtable/_vendored/connector_sdk/constants.py +78 -0
  10. airbyte_agent_airtable/_vendored/connector_sdk/exceptions.py +23 -0
  11. airbyte_agent_airtable/_vendored/connector_sdk/executor/__init__.py +31 -0
  12. airbyte_agent_airtable/_vendored/connector_sdk/executor/hosted_executor.py +230 -0
  13. airbyte_agent_airtable/_vendored/connector_sdk/executor/local_executor.py +1848 -0
  14. airbyte_agent_airtable/_vendored/connector_sdk/executor/models.py +202 -0
  15. airbyte_agent_airtable/_vendored/connector_sdk/extensions.py +693 -0
  16. airbyte_agent_airtable/_vendored/connector_sdk/http/__init__.py +37 -0
  17. airbyte_agent_airtable/_vendored/connector_sdk/http/adapters/__init__.py +9 -0
  18. airbyte_agent_airtable/_vendored/connector_sdk/http/adapters/httpx_adapter.py +260 -0
  19. airbyte_agent_airtable/_vendored/connector_sdk/http/config.py +98 -0
  20. airbyte_agent_airtable/_vendored/connector_sdk/http/exceptions.py +119 -0
  21. airbyte_agent_airtable/_vendored/connector_sdk/http/protocols.py +114 -0
  22. airbyte_agent_airtable/_vendored/connector_sdk/http/response.py +104 -0
  23. airbyte_agent_airtable/_vendored/connector_sdk/http_client.py +693 -0
  24. airbyte_agent_airtable/_vendored/connector_sdk/introspection.py +481 -0
  25. airbyte_agent_airtable/_vendored/connector_sdk/logging/__init__.py +11 -0
  26. airbyte_agent_airtable/_vendored/connector_sdk/logging/logger.py +273 -0
  27. airbyte_agent_airtable/_vendored/connector_sdk/logging/types.py +93 -0
  28. airbyte_agent_airtable/_vendored/connector_sdk/observability/__init__.py +11 -0
  29. airbyte_agent_airtable/_vendored/connector_sdk/observability/config.py +179 -0
  30. airbyte_agent_airtable/_vendored/connector_sdk/observability/models.py +19 -0
  31. airbyte_agent_airtable/_vendored/connector_sdk/observability/redactor.py +81 -0
  32. airbyte_agent_airtable/_vendored/connector_sdk/observability/session.py +103 -0
  33. airbyte_agent_airtable/_vendored/connector_sdk/performance/__init__.py +6 -0
  34. airbyte_agent_airtable/_vendored/connector_sdk/performance/instrumentation.py +57 -0
  35. airbyte_agent_airtable/_vendored/connector_sdk/performance/metrics.py +93 -0
  36. airbyte_agent_airtable/_vendored/connector_sdk/schema/__init__.py +75 -0
  37. airbyte_agent_airtable/_vendored/connector_sdk/schema/base.py +212 -0
  38. airbyte_agent_airtable/_vendored/connector_sdk/schema/components.py +244 -0
  39. airbyte_agent_airtable/_vendored/connector_sdk/schema/connector.py +120 -0
  40. airbyte_agent_airtable/_vendored/connector_sdk/schema/extensions.py +301 -0
  41. airbyte_agent_airtable/_vendored/connector_sdk/schema/operations.py +156 -0
  42. airbyte_agent_airtable/_vendored/connector_sdk/schema/security.py +241 -0
  43. airbyte_agent_airtable/_vendored/connector_sdk/secrets.py +182 -0
  44. airbyte_agent_airtable/_vendored/connector_sdk/telemetry/__init__.py +10 -0
  45. airbyte_agent_airtable/_vendored/connector_sdk/telemetry/config.py +32 -0
  46. airbyte_agent_airtable/_vendored/connector_sdk/telemetry/events.py +59 -0
  47. airbyte_agent_airtable/_vendored/connector_sdk/telemetry/tracker.py +155 -0
  48. airbyte_agent_airtable/_vendored/connector_sdk/types.py +274 -0
  49. airbyte_agent_airtable/_vendored/connector_sdk/utils.py +127 -0
  50. airbyte_agent_airtable/_vendored/connector_sdk/validation.py +997 -0
  51. airbyte_agent_airtable/_vendored/connector_sdk/validation_replication.py +970 -0
  52. airbyte_agent_airtable/connector.py +834 -0
  53. airbyte_agent_airtable/connector_model.py +365 -0
  54. airbyte_agent_airtable/models.py +219 -0
  55. airbyte_agent_airtable/types.py +367 -0
  56. airbyte_agent_airtable-0.1.5.dist-info/METADATA +140 -0
  57. airbyte_agent_airtable-0.1.5.dist-info/RECORD +58 -0
  58. airbyte_agent_airtable-0.1.5.dist-info/WHEEL +4 -0
@@ -0,0 +1,365 @@
1
+ """
2
+ Connector model for airtable.
3
+
4
+ This file is auto-generated from the connector definition at build time.
5
+ DO NOT EDIT MANUALLY - changes will be overwritten on next generation.
6
+ """
7
+
8
+ from __future__ import annotations
9
+
10
+ from ._vendored.connector_sdk.types import (
11
+ Action,
12
+ AuthConfig,
13
+ AuthType,
14
+ ConnectorModel,
15
+ EndpointDefinition,
16
+ EntityDefinition,
17
+ )
18
+ from ._vendored.connector_sdk.schema.security import (
19
+ AirbyteAuthConfig,
20
+ AuthConfigFieldSpec,
21
+ )
22
+ from uuid import (
23
+ UUID,
24
+ )
25
+
26
+ AirtableConnectorModel: ConnectorModel = ConnectorModel(
27
+ id=UUID('14c6e7ea-97ed-4f5e-a7b5-25e9a80b8212'),
28
+ name='airtable',
29
+ version='1.0.2',
30
+ base_url='https://api.airtable.com/v0',
31
+ auth=AuthConfig(
32
+ type=AuthType.BEARER,
33
+ config={'header': 'Authorization', 'prefix': 'Bearer'},
34
+ user_config_spec=AirbyteAuthConfig(
35
+ title='Personal Access Token',
36
+ type='object',
37
+ required=['personal_access_token'],
38
+ properties={
39
+ 'personal_access_token': AuthConfigFieldSpec(
40
+ title='Personal Access Token',
41
+ description='Airtable Personal Access Token. See https://airtable.com/developers/web/guides/personal-access-tokens',
42
+ ),
43
+ },
44
+ auth_mapping={'token': '${personal_access_token}'},
45
+ replication_auth_key_mapping={'credentials.api_key': 'personal_access_token'},
46
+ ),
47
+ ),
48
+ entities=[
49
+ EntityDefinition(
50
+ name='bases',
51
+ stream_name='bases',
52
+ actions=[Action.LIST],
53
+ endpoints={
54
+ Action.LIST: EndpointDefinition(
55
+ method='GET',
56
+ path='/meta/bases',
57
+ action=Action.LIST,
58
+ description='Returns a list of all bases the user has access to',
59
+ query_params=['offset'],
60
+ query_params_schema={
61
+ 'offset': {'type': 'string', 'required': False},
62
+ },
63
+ response_schema={
64
+ 'type': 'object',
65
+ 'description': 'Paginated list of bases',
66
+ 'properties': {
67
+ 'bases': {
68
+ 'type': 'array',
69
+ 'items': {
70
+ 'type': 'object',
71
+ 'description': 'An Airtable base (workspace)',
72
+ 'properties': {
73
+ 'id': {'type': 'string', 'description': 'Unique identifier for the base'},
74
+ 'name': {
75
+ 'type': ['string', 'null'],
76
+ 'description': 'Name of the base',
77
+ },
78
+ 'permissionLevel': {
79
+ 'type': ['string', 'null'],
80
+ 'description': 'Permission level for the base (e.g., owner, editor, commenter, read)',
81
+ },
82
+ },
83
+ 'required': ['id'],
84
+ 'x-airbyte-entity-name': 'bases',
85
+ 'x-airbyte-stream-name': 'bases',
86
+ },
87
+ },
88
+ 'offset': {
89
+ 'type': ['string', 'null'],
90
+ 'description': 'Pagination offset for next page',
91
+ },
92
+ },
93
+ },
94
+ record_extractor='$.bases',
95
+ ),
96
+ },
97
+ entity_schema={
98
+ 'type': 'object',
99
+ 'description': 'An Airtable base (workspace)',
100
+ 'properties': {
101
+ 'id': {'type': 'string', 'description': 'Unique identifier for the base'},
102
+ 'name': {
103
+ 'type': ['string', 'null'],
104
+ 'description': 'Name of the base',
105
+ },
106
+ 'permissionLevel': {
107
+ 'type': ['string', 'null'],
108
+ 'description': 'Permission level for the base (e.g., owner, editor, commenter, read)',
109
+ },
110
+ },
111
+ 'required': ['id'],
112
+ 'x-airbyte-entity-name': 'bases',
113
+ 'x-airbyte-stream-name': 'bases',
114
+ },
115
+ ),
116
+ EntityDefinition(
117
+ name='tables',
118
+ stream_name='tables',
119
+ actions=[Action.LIST],
120
+ endpoints={
121
+ Action.LIST: EndpointDefinition(
122
+ method='GET',
123
+ path='/meta/bases/{base_id}/tables',
124
+ action=Action.LIST,
125
+ description='Returns a list of all tables in the specified base with their schema information',
126
+ path_params=['base_id'],
127
+ path_params_schema={
128
+ 'base_id': {'type': 'string', 'required': True},
129
+ },
130
+ response_schema={
131
+ 'type': 'object',
132
+ 'description': 'List of tables in a base',
133
+ 'properties': {
134
+ 'tables': {
135
+ 'type': 'array',
136
+ 'items': {
137
+ 'type': 'object',
138
+ 'description': 'A table within an Airtable base',
139
+ 'properties': {
140
+ 'id': {'type': 'string', 'description': 'Unique identifier for the table'},
141
+ 'name': {
142
+ 'type': ['string', 'null'],
143
+ 'description': 'Name of the table',
144
+ },
145
+ 'primaryFieldId': {
146
+ 'type': ['string', 'null'],
147
+ 'description': 'ID of the primary field',
148
+ },
149
+ 'fields': {
150
+ 'type': ['array', 'null'],
151
+ 'description': 'List of fields in the table',
152
+ 'items': {
153
+ 'type': 'object',
154
+ 'description': 'A field (column) in a table',
155
+ 'properties': {
156
+ 'id': {
157
+ 'type': ['string', 'null'],
158
+ 'description': 'Unique identifier for the field',
159
+ },
160
+ 'name': {
161
+ 'type': ['string', 'null'],
162
+ 'description': 'Name of the field',
163
+ },
164
+ 'type': {
165
+ 'type': ['string', 'null'],
166
+ 'description': 'Type of the field (e.g., singleLineText, number, checkbox)',
167
+ },
168
+ 'options': {
169
+ 'type': ['object', 'null'],
170
+ 'description': 'Field-specific options',
171
+ 'additionalProperties': True,
172
+ },
173
+ },
174
+ },
175
+ },
176
+ 'views': {
177
+ 'type': ['array', 'null'],
178
+ 'description': 'List of views in the table',
179
+ 'items': {
180
+ 'type': 'object',
181
+ 'description': 'A view in a table',
182
+ 'properties': {
183
+ 'id': {
184
+ 'type': ['string', 'null'],
185
+ 'description': 'Unique identifier for the view',
186
+ },
187
+ 'name': {
188
+ 'type': ['string', 'null'],
189
+ 'description': 'Name of the view',
190
+ },
191
+ 'type': {
192
+ 'type': ['string', 'null'],
193
+ 'description': 'Type of the view (e.g., grid, form, calendar)',
194
+ },
195
+ },
196
+ },
197
+ },
198
+ },
199
+ 'required': ['id'],
200
+ 'x-airbyte-entity-name': 'tables',
201
+ 'x-airbyte-stream-name': 'tables',
202
+ },
203
+ },
204
+ },
205
+ },
206
+ record_extractor='$.tables',
207
+ ),
208
+ },
209
+ entity_schema={
210
+ 'type': 'object',
211
+ 'description': 'A table within an Airtable base',
212
+ 'properties': {
213
+ 'id': {'type': 'string', 'description': 'Unique identifier for the table'},
214
+ 'name': {
215
+ 'type': ['string', 'null'],
216
+ 'description': 'Name of the table',
217
+ },
218
+ 'primaryFieldId': {
219
+ 'type': ['string', 'null'],
220
+ 'description': 'ID of the primary field',
221
+ },
222
+ 'fields': {
223
+ 'type': ['array', 'null'],
224
+ 'description': 'List of fields in the table',
225
+ 'items': {'$ref': '#/components/schemas/TableField'},
226
+ },
227
+ 'views': {
228
+ 'type': ['array', 'null'],
229
+ 'description': 'List of views in the table',
230
+ 'items': {'$ref': '#/components/schemas/View'},
231
+ },
232
+ },
233
+ 'required': ['id'],
234
+ 'x-airbyte-entity-name': 'tables',
235
+ 'x-airbyte-stream-name': 'tables',
236
+ },
237
+ ),
238
+ EntityDefinition(
239
+ name='records',
240
+ actions=[Action.LIST, Action.GET],
241
+ endpoints={
242
+ Action.LIST: EndpointDefinition(
243
+ method='GET',
244
+ path='/{base_id}/{table_id_or_name}',
245
+ action=Action.LIST,
246
+ description='Returns a paginated list of records from the specified table',
247
+ query_params=[
248
+ 'offset',
249
+ 'pageSize',
250
+ 'view',
251
+ 'filterByFormula',
252
+ 'sort',
253
+ ],
254
+ query_params_schema={
255
+ 'offset': {'type': 'string', 'required': False},
256
+ 'pageSize': {'type': 'integer', 'required': False},
257
+ 'view': {'type': 'string', 'required': False},
258
+ 'filterByFormula': {'type': 'string', 'required': False},
259
+ 'sort': {'type': 'string', 'required': False},
260
+ },
261
+ path_params=['base_id', 'table_id_or_name'],
262
+ path_params_schema={
263
+ 'base_id': {'type': 'string', 'required': True},
264
+ 'table_id_or_name': {'type': 'string', 'required': True},
265
+ },
266
+ response_schema={
267
+ 'type': 'object',
268
+ 'description': 'Paginated list of records',
269
+ 'properties': {
270
+ 'records': {
271
+ 'type': 'array',
272
+ 'items': {
273
+ 'type': 'object',
274
+ 'description': 'A record (row) in an Airtable table',
275
+ 'properties': {
276
+ 'id': {'type': 'string', 'description': 'Unique identifier for the record'},
277
+ 'createdTime': {
278
+ 'type': ['string', 'null'],
279
+ 'format': 'date-time',
280
+ 'description': 'Timestamp when the record was created',
281
+ },
282
+ 'fields': {
283
+ 'type': ['object', 'null'],
284
+ 'description': 'Field values for the record',
285
+ 'additionalProperties': True,
286
+ },
287
+ },
288
+ 'required': ['id'],
289
+ 'x-airbyte-entity-name': 'records',
290
+ },
291
+ },
292
+ 'offset': {
293
+ 'type': ['string', 'null'],
294
+ 'description': 'Pagination offset for next page',
295
+ },
296
+ },
297
+ },
298
+ record_extractor='$.records',
299
+ ),
300
+ Action.GET: EndpointDefinition(
301
+ method='GET',
302
+ path='/{base_id}/{table_id_or_name}/{record_id}',
303
+ action=Action.GET,
304
+ description='Returns a single record by ID from the specified table',
305
+ path_params=['base_id', 'table_id_or_name', 'record_id'],
306
+ path_params_schema={
307
+ 'base_id': {'type': 'string', 'required': True},
308
+ 'table_id_or_name': {'type': 'string', 'required': True},
309
+ 'record_id': {'type': 'string', 'required': True},
310
+ },
311
+ response_schema={
312
+ 'type': 'object',
313
+ 'description': 'A record (row) in an Airtable table',
314
+ 'properties': {
315
+ 'id': {'type': 'string', 'description': 'Unique identifier for the record'},
316
+ 'createdTime': {
317
+ 'type': ['string', 'null'],
318
+ 'format': 'date-time',
319
+ 'description': 'Timestamp when the record was created',
320
+ },
321
+ 'fields': {
322
+ 'type': ['object', 'null'],
323
+ 'description': 'Field values for the record',
324
+ 'additionalProperties': True,
325
+ },
326
+ },
327
+ 'required': ['id'],
328
+ 'x-airbyte-entity-name': 'records',
329
+ },
330
+ ),
331
+ },
332
+ entity_schema={
333
+ 'type': 'object',
334
+ 'description': 'A record (row) in an Airtable table',
335
+ 'properties': {
336
+ 'id': {'type': 'string', 'description': 'Unique identifier for the record'},
337
+ 'createdTime': {
338
+ 'type': ['string', 'null'],
339
+ 'format': 'date-time',
340
+ 'description': 'Timestamp when the record was created',
341
+ },
342
+ 'fields': {
343
+ 'type': ['object', 'null'],
344
+ 'description': 'Field values for the record',
345
+ 'additionalProperties': True,
346
+ },
347
+ },
348
+ 'required': ['id'],
349
+ 'x-airbyte-entity-name': 'records',
350
+ },
351
+ ),
352
+ ],
353
+ search_field_paths={
354
+ 'bases': ['id', 'name', 'permissionLevel'],
355
+ 'tables': [
356
+ 'id',
357
+ 'name',
358
+ 'primaryFieldId',
359
+ 'fields',
360
+ 'fields[]',
361
+ 'views',
362
+ 'views[]',
363
+ ],
364
+ },
365
+ )
@@ -0,0 +1,219 @@
1
+ """
2
+ Pydantic models for airtable connector.
3
+
4
+ This module contains Pydantic models used for authentication configuration
5
+ and response envelope types.
6
+ """
7
+
8
+ from __future__ import annotations
9
+
10
+ from pydantic import BaseModel, ConfigDict, Field
11
+ from typing import TypeVar, Generic, Union, Any
12
+
13
+ # Authentication configuration
14
+
15
+ class AirtableAuthConfig(BaseModel):
16
+ """Personal Access Token"""
17
+
18
+ model_config = ConfigDict(extra="forbid")
19
+
20
+ personal_access_token: str
21
+ """Airtable Personal Access Token. See https://airtable.com/developers/web/guides/personal-access-tokens"""
22
+
23
+ # ===== RESPONSE TYPE DEFINITIONS (PYDANTIC) =====
24
+
25
+ class Base(BaseModel):
26
+ """An Airtable base (workspace)"""
27
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
28
+
29
+ id: Union[str, Any] = Field(default=None)
30
+ name: Union[str | None, Any] = Field(default=None)
31
+ permission_level: Union[str | None, Any] = Field(default=None, alias="permissionLevel")
32
+
33
+ class BasesList(BaseModel):
34
+ """Paginated list of bases"""
35
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
36
+
37
+ bases: Union[list[Base], Any] = Field(default=None)
38
+ offset: Union[str | None, Any] = Field(default=None)
39
+
40
+ class TableField(BaseModel):
41
+ """A field (column) in a table"""
42
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
43
+
44
+ id: Union[str | None, Any] = Field(default=None)
45
+ name: Union[str | None, Any] = Field(default=None)
46
+ type: Union[str | None, Any] = Field(default=None)
47
+ options: Union[dict[str, Any] | None, Any] = Field(default=None)
48
+
49
+ class View(BaseModel):
50
+ """A view in a table"""
51
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
52
+
53
+ id: Union[str | None, Any] = Field(default=None)
54
+ name: Union[str | None, Any] = Field(default=None)
55
+ type: Union[str | None, Any] = Field(default=None)
56
+
57
+ class Table(BaseModel):
58
+ """A table within an Airtable base"""
59
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
60
+
61
+ id: Union[str, Any] = Field(default=None)
62
+ name: Union[str | None, Any] = Field(default=None)
63
+ primary_field_id: Union[str | None, Any] = Field(default=None, alias="primaryFieldId")
64
+ fields: Union[list[TableField] | None, Any] = Field(default=None)
65
+ views: Union[list[View] | None, Any] = Field(default=None)
66
+
67
+ class TablesList(BaseModel):
68
+ """List of tables in a base"""
69
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
70
+
71
+ tables: Union[list[Table], Any] = Field(default=None)
72
+
73
+ class Record(BaseModel):
74
+ """A record (row) in an Airtable table"""
75
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
76
+
77
+ id: Union[str, Any] = Field(default=None)
78
+ created_time: Union[str | None, Any] = Field(default=None, alias="createdTime")
79
+ fields: Union[dict[str, Any] | None, Any] = Field(default=None)
80
+
81
+ class RecordsList(BaseModel):
82
+ """Paginated list of records"""
83
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
84
+
85
+ records: Union[list[Record], Any] = Field(default=None)
86
+ offset: Union[str | None, Any] = Field(default=None)
87
+
88
+ # ===== METADATA TYPE DEFINITIONS (PYDANTIC) =====
89
+ # Meta types for operations that extract metadata (e.g., pagination info)
90
+
91
+ # ===== CHECK RESULT MODEL =====
92
+
93
+ class AirtableCheckResult(BaseModel):
94
+ """Result of a health check operation.
95
+
96
+ Returned by the check() method to indicate connectivity and credential status.
97
+ """
98
+ model_config = ConfigDict(extra="forbid")
99
+
100
+ status: str
101
+ """Health check status: 'healthy' or 'unhealthy'."""
102
+ error: str | None = None
103
+ """Error message if status is 'unhealthy', None otherwise."""
104
+ checked_entity: str | None = None
105
+ """Entity name used for the health check."""
106
+ checked_action: str | None = None
107
+ """Action name used for the health check."""
108
+
109
+
110
+ # ===== RESPONSE ENVELOPE MODELS =====
111
+
112
+ # Type variables for generic envelope models
113
+ T = TypeVar('T')
114
+ S = TypeVar('S')
115
+
116
+
117
+ class AirtableExecuteResult(BaseModel, Generic[T]):
118
+ """Response envelope with data only.
119
+
120
+ Used for actions that return data without metadata.
121
+ """
122
+ model_config = ConfigDict(extra="forbid")
123
+
124
+ data: T
125
+ """Response data containing the result of the action."""
126
+
127
+
128
+ class AirtableExecuteResultWithMeta(AirtableExecuteResult[T], Generic[T, S]):
129
+ """Response envelope with data and metadata.
130
+
131
+ Used for actions that return both data and metadata (e.g., pagination info).
132
+ """
133
+ meta: S
134
+ """Metadata about the response (e.g., pagination cursors, record counts)."""
135
+
136
+ # ===== SEARCH DATA MODELS =====
137
+ # Entity-specific Pydantic models for search result data
138
+
139
+ # Type variable for search data generic
140
+ D = TypeVar('D')
141
+
142
+ class BasesSearchData(BaseModel):
143
+ """Search result data for bases entity."""
144
+ model_config = ConfigDict(extra="allow")
145
+
146
+ id: str | None = None
147
+ """Unique identifier for the base"""
148
+ name: str | None = None
149
+ """Name of the base"""
150
+ permission_level: str | None = None
151
+ """Permission level for the base"""
152
+
153
+
154
+ class TablesSearchData(BaseModel):
155
+ """Search result data for tables entity."""
156
+ model_config = ConfigDict(extra="allow")
157
+
158
+ id: str | None = None
159
+ """Unique identifier for the table"""
160
+ name: str | None = None
161
+ """Name of the table"""
162
+ primary_field_id: str | None = None
163
+ """ID of the primary field"""
164
+ fields: list[Any] | None = None
165
+ """List of fields in the table"""
166
+ views: list[Any] | None = None
167
+ """List of views in the table"""
168
+
169
+
170
+ # ===== GENERIC SEARCH RESULT TYPES =====
171
+
172
+ class AirbyteSearchHit(BaseModel, Generic[D]):
173
+ """A single search result with typed data."""
174
+ model_config = ConfigDict(extra="allow")
175
+
176
+ id: str | None = None
177
+ """Unique identifier for the record."""
178
+ score: float | None = None
179
+ """Relevance score for the match."""
180
+ data: D
181
+ """The matched record data."""
182
+
183
+
184
+ class AirbyteSearchResult(BaseModel, Generic[D]):
185
+ """Result from Airbyte cache search operations with typed hits."""
186
+ model_config = ConfigDict(extra="allow")
187
+
188
+ hits: list[AirbyteSearchHit[D]] = Field(default_factory=list)
189
+ """List of matching records."""
190
+ next_cursor: str | None = None
191
+ """Cursor for fetching the next page of results."""
192
+ took_ms: int | None = None
193
+ """Time taken to execute the search in milliseconds."""
194
+
195
+
196
+ # ===== ENTITY-SPECIFIC SEARCH RESULT TYPE ALIASES =====
197
+
198
+ BasesSearchResult = AirbyteSearchResult[BasesSearchData]
199
+ """Search result type for bases entity."""
200
+
201
+ TablesSearchResult = AirbyteSearchResult[TablesSearchData]
202
+ """Search result type for tables entity."""
203
+
204
+
205
+
206
+ # ===== OPERATION RESULT TYPE ALIASES =====
207
+
208
+ # Concrete type aliases for each operation result.
209
+ # These provide simpler, more readable type annotations than using the generic forms.
210
+
211
+ BasesListResult = AirtableExecuteResult[list[Base]]
212
+ """Result type for bases.list operation."""
213
+
214
+ TablesListResult = AirtableExecuteResult[list[Table]]
215
+ """Result type for tables.list operation."""
216
+
217
+ RecordsListResult = AirtableExecuteResult[list[Record]]
218
+ """Result type for records.list operation."""
219
+