squidcloud
Squid Cloud Python client SDK.
Usage::
from squidcloud import Squid
squid = Squid(
app_id="my-app",
api_key="my-api-key",
region="us-east-1.aws",
environment_id="dev",
)
# AI agents
response = await squid.ai().agent("my-agent").ask("Hello!")
# Execute backend function
result = await squid.execute_function("MyService:greet", "World")
# Web utilities
content = await squid.web().get_url_content("https://example.com")
1"""Squid Cloud Python client SDK. 2 3Usage:: 4 5 from squidcloud import Squid 6 7 squid = Squid( 8 app_id="my-app", 9 api_key="my-api-key", 10 region="us-east-1.aws", 11 environment_id="dev", 12 ) 13 14 # AI agents 15 response = await squid.ai().agent("my-agent").ask("Hello!") 16 17 # Execute backend function 18 result = await squid.execute_function("MyService:greet", "World") 19 20 # Web utilities 21 content = await squid.web().get_url_content("https://example.com") 22""" 23 24from squidcloud.ai import ( 25 AgentClient, 26 AiClient, 27 AudioClient, 28 ImageClient, 29 KnowledgeBaseClient, 30) 31from squidcloud.client import Squid 32from squidcloud.extraction import ExtractionClient 33from squidcloud.http import SquidHttpError 34from squidcloud.matchmaking import MatchmakingClient 35from squidcloud.types import ( 36 AiAgent, 37 AiAgentExecutionPlanOptions, 38 AiAgentMemoryOptions, 39 AiAgentResponseFormat, 40 AiAudioCreateSpeechOptions, 41 AiChatModelSelection, 42 AiChatOptions, 43 AiChatPromptQuotas, 44 AiConnectedAgentMetadata, 45 AiConnectedIntegrationMetadata, 46 AiConnectedKnowledgeBaseMetadata, 47 AiContextFileOptions, 48 AiContextTextOptions, 49 AiEmbeddingsModelSelection, 50 AiFileUrl, 51 AiFunctionAttributes, 52 AiFunctionMetadata, 53 AiFunctionParam, 54 AiKnowledgeBase, 55 AiKnowledgeBaseMetadataField, 56 AiQueryAnalyzeResultsOptions, 57 AiQueryCollectionsSelectionRunMode, 58 AiQueryGenerateQueryOptions, 59 AiQueryOptions, 60 AiQuerySelectCollectionsOptions, 61 AiQueryValidateWithAiOptions, 62 AiSessionContext, 63 AiStructuredOutputFormat, 64 ContextRequest, 65 CreatePdfDimensionsOptions, 66 CreatePdfFormatOptions, 67 CreatePdfOutputOptions, 68 ExtractDataFromDocumentOptions, 69 FileContextRequest, 70 FluxOptions, 71 GptImageOptions, 72 GuardrailsOptions, 73 ImageGenerateOptions, 74 IntegrationEmbeddingModelSpec, 75 IntegrationModelSpec, 76 KnowledgeBaseSearchOptions, 77 MmCategory, 78 MmEntity, 79 MmFindMatchesOptions, 80 MmListEntitiesOptions, 81 ModelIdSpec, 82 StableDiffusionOptions, 83 TextContextRequest, 84 UpsertAgentOptions, 85 WebAiSearchResponse, 86 WebShortUrlBulkResponse, 87 WebShortUrlResponse, 88) 89from squidcloud.web import WebClient 90 91__all__ = [ 92 "AgentClient", 93 "AiAgent", 94 "AiAgentExecutionPlanOptions", 95 "AiAgentMemoryOptions", 96 "AiAgentResponseFormat", 97 "AiAudioCreateSpeechOptions", 98 "AiChatModelSelection", 99 # AI Chat 100 "AiChatOptions", 101 "AiChatPromptQuotas", 102 "AiClient", 103 "AiConnectedAgentMetadata", 104 "AiConnectedIntegrationMetadata", 105 "AiConnectedKnowledgeBaseMetadata", 106 "AiContextFileOptions", 107 "AiContextTextOptions", 108 "AiEmbeddingsModelSelection", 109 "AiFileUrl", 110 "AiFunctionAttributes", 111 "AiFunctionMetadata", 112 "AiFunctionParam", 113 # Knowledge Base 114 "AiKnowledgeBase", 115 "AiKnowledgeBaseMetadataField", 116 # AI Query 117 "AiQueryAnalyzeResultsOptions", 118 "AiQueryCollectionsSelectionRunMode", 119 "AiQueryGenerateQueryOptions", 120 "AiQueryOptions", 121 "AiQuerySelectCollectionsOptions", 122 "AiQueryValidateWithAiOptions", 123 "AiSessionContext", 124 "AiStructuredOutputFormat", 125 "AudioClient", 126 "ContextRequest", 127 "CreatePdfDimensionsOptions", 128 "CreatePdfFormatOptions", 129 # Extraction 130 "CreatePdfOutputOptions", 131 "ExtractDataFromDocumentOptions", 132 "ExtractionClient", 133 "FileContextRequest", 134 "FluxOptions", 135 "GptImageOptions", 136 "GuardrailsOptions", 137 # Image 138 "ImageClient", 139 "ImageGenerateOptions", 140 "IntegrationEmbeddingModelSpec", 141 "IntegrationModelSpec", 142 "KnowledgeBaseClient", 143 "KnowledgeBaseSearchOptions", 144 # Matchmaking 145 "MatchmakingClient", 146 "MmCategory", 147 "MmEntity", 148 "MmFindMatchesOptions", 149 "MmListEntitiesOptions", 150 "ModelIdSpec", 151 "Squid", 152 "SquidHttpError", 153 "StableDiffusionOptions", 154 "TextContextRequest", 155 "UpsertAgentOptions", 156 # Web 157 "WebAiSearchResponse", 158 "WebClient", 159 "WebShortUrlBulkResponse", 160 "WebShortUrlResponse", 161]
141class AgentClient: 142 """Operations on a single AI agent. 143 144 Provides methods for chatting with an agent, managing its configuration, 145 updating guardrails, and working with revisions. 146 147 Obtained via :meth:`AiClient.agent`. 148 149 Example:: 150 151 agent = squid.ai().agent("my-agent") 152 response = await agent.ask("What is the weather?", options={"temperature": 0.7}) 153 await agent.update_instructions("Always respond in haiku format.") 154 """ 155 156 def __init__(self, http: HttpTransport, agent_id: str) -> None: 157 self._http = http 158 self._agent_id = agent_id 159 160 # --- Chat --- 161 162 async def ask( 163 self, 164 prompt: str, 165 options: AiChatOptions | None = None, 166 ) -> str: 167 """Ask the agent a question and get a text response. 168 169 Args: 170 prompt: The user's question or instruction. 171 options: Chat options controlling model, temperature, memory, 172 functions, guardrails, and more. See :class:`AiChatOptions`. 173 174 Returns: 175 The agent's response as a string. 176 177 Raises: 178 SquidHttpError: If the agent is not found or the request fails. 179 180 Example:: 181 182 response = await agent.ask( 183 "Summarize this document", 184 options={ 185 "model": "gemini-3-flash", 186 "temperature": 0.3, 187 "memoryOptions": {"memoryId": "session-1", "memoryMode": "read-write"}, 188 }, 189 ) 190 """ 191 result = await self._http.post( 192 "squid-api/v1/ai/agent/ask", 193 {"agentId": self._agent_id, "prompt": prompt, "options": options or {}}, 194 ) 195 return result.get("responseString", "") if result else "" 196 197 async def ask_with_annotations( 198 self, 199 prompt: str, 200 options: AiChatOptions | None = None, 201 ) -> dict: 202 """Ask the agent and get a response with annotations. 203 204 Annotations include file references, citations, and other metadata 205 the agent may attach to its response. 206 207 Args: 208 prompt: The user's question or instruction. 209 options: Chat options. See :class:`AiChatOptions`. 210 211 Returns: 212 A dict with: 213 - ``responseString`` (str): The text response. 214 - ``annotations`` (dict): Annotation metadata keyed by ID. 215 216 Example:: 217 218 result = await agent.ask_with_annotations("Find relevant docs") 219 print(result["responseString"]) 220 for ann_id, ann in result.get("annotations", {}).items(): 221 print(f" Annotation: {ann}") 222 """ 223 return await self._http.post( 224 "squid-api/v1/ai/agent/askWithAnnotations", 225 {"agentId": self._agent_id, "prompt": prompt, "options": options or {}}, 226 ) 227 228 # --- Management --- 229 230 async def get(self) -> dict | None: 231 """Get the agent's configuration. 232 233 Returns: 234 An ``AiAgent`` dict with keys: ``id``, ``createdAt``, ``updatedAt``, 235 ``description``, ``isPublic``, ``auditLog``, ``options``, ``apiKey``. 236 Returns ``None`` if the agent does not exist. 237 """ 238 return await self._http.get(f"squid-api/v1/ai/agent/get/{self._agent_id}") 239 240 async def upsert( 241 self, 242 *, 243 description: str | None = None, 244 is_public: bool | None = None, 245 audit_log: bool | None = None, 246 api_key: str | None = None, 247 options: AiChatOptions | None = None, 248 ) -> None: 249 """Create or update the agent. 250 251 If the agent does not exist, it is created. If it exists, the provided 252 fields are updated (fields set to ``None`` are left unchanged). 253 254 Args: 255 description: A description of the agent's purpose or capabilities. 256 is_public: Whether the agent is publicly accessible (default ``False``). 257 audit_log: Enable audit logging for the agent's activities. 258 api_key: Optional API key used specifically for this agent. 259 options: Default chat options applied to every request unless 260 overridden per-call. See :class:`AiChatOptions`. 261 262 Example:: 263 264 await agent.upsert( 265 description="Customer support agent", 266 options={"model": "gemini-3-flash", "temperature": 0.5}, 267 ) 268 """ 269 body: dict[str, Any] = {"id": self._agent_id} 270 if description is not None: 271 body["description"] = description 272 if is_public is not None: 273 body["isPublic"] = is_public 274 if audit_log is not None: 275 body["auditLog"] = audit_log 276 if api_key is not None: 277 body["apiKey"] = api_key 278 if options is not None: 279 body["options"] = options 280 await self._http.post("squid-api/v1/ai/agent/upsert", body) 281 282 async def delete(self) -> None: 283 """Delete the agent permanently.""" 284 await self._http.post("squid-api/v1/ai/agent/delete", {"agentId": self._agent_id}) 285 286 async def update_instructions(self, instructions: str) -> None: 287 """Update the agent's system instructions. 288 289 Args: 290 instructions: The new system prompt / instructions text. 291 """ 292 await self._http.post( 293 "squid-api/v1/ai/agent/updateInstructions", 294 {"agentId": self._agent_id, "instructions": instructions}, 295 ) 296 297 async def update_model(self, model: AiChatModelSelection) -> None: 298 """Update the agent's default LLM model. 299 300 Args: 301 model: A model name string (e.g., ``'gemini-3-flash'``) or an 302 ``IntegrationModelSpec`` dict (``{'integrationId': str, 'model': str}``). 303 """ 304 await self._http.post( 305 "squid-api/v1/ai/agent/updateModel", 306 {"agentId": self._agent_id, "model": model}, 307 ) 308 309 async def update_connected_agents( 310 self, connected_agents: list[AiConnectedAgentMetadata] 311 ) -> None: 312 """Update the list of connected agents. 313 314 Connected agents can be called by this agent during conversations. 315 316 Args: 317 connected_agents: List of ``{'agentId': str, 'description': str}`` dicts. 318 """ 319 await self._http.post( 320 "squid-api/v1/ai/agent/updateConnectedAgents", 321 {"agentId": self._agent_id, "connectedAgents": connected_agents}, 322 ) 323 324 async def update_guardrails(self, guardrails: GuardrailsOptions) -> None: 325 """Update the agent's guardrail settings. 326 327 Args: 328 guardrails: A :class:`GuardrailsOptions` dict with optional keys: 329 ``custom``, ``disablePii``, ``professionalTone``, 330 ``offTopicAnswers``, ``disableProfanity``. 331 332 Example:: 333 334 await agent.update_guardrails( 335 { 336 "professionalTone": True, 337 "disableProfanity": True, 338 } 339 ) 340 """ 341 await self._http.post( 342 "squid-api/v1/ai/agent/updateGuardrails", 343 {"agentId": self._agent_id, "guardrails": guardrails}, 344 ) 345 346 async def update_custom_guardrails(self, custom_guardrail: str) -> None: 347 """Update the custom guardrail instruction text. 348 349 Args: 350 custom_guardrail: Free-form guardrail instruction string. 351 """ 352 await self._http.post( 353 "squid-api/v1/ai/agent/updateCustomGuardrails", 354 {"agentId": self._agent_id, "customGuardrail": custom_guardrail}, 355 ) 356 357 async def delete_custom_guardrails(self) -> None: 358 """Delete the custom guardrail, reverting to defaults.""" 359 await self._http.post( 360 "squid-api/v1/ai/agent/deleteCustomGuardrails", 361 {"agentId": self._agent_id}, 362 ) 363 364 # --- Revisions --- 365 366 async def list_revisions(self) -> list[dict]: 367 """List all revisions of this agent. 368 369 Returns: 370 A list of ``AiAgentRevision`` dicts, each containing: 371 ``agentId``, ``revisionNumber``, ``action``, ``createdAt``, 372 ``agentSnapshot``. 373 """ 374 result = await self._http.get(f"squid-api/v1/ai/agent/revisions/{self._agent_id}") 375 return result.get("revisions", []) if result else [] 376 377 async def restore_revision(self, revision_number: int) -> None: 378 """Restore the agent to a previous revision. 379 380 Args: 381 revision_number: The revision number to restore. 382 """ 383 await self._http.post( 384 "squid-api/v1/ai/agent/restoreRevision", 385 {"agentId": self._agent_id, "revisionNumber": revision_number}, 386 ) 387 388 async def delete_revision(self, revision_number: int) -> None: 389 """Delete a specific revision. 390 391 Args: 392 revision_number: The revision number to delete. 393 """ 394 await self._http.post( 395 "squid-api/v1/ai/agent/deleteRevision", 396 {"agentId": self._agent_id, "revisionNumber": revision_number}, 397 )
Operations on a single AI agent.
Provides methods for chatting with an agent, managing its configuration, updating guardrails, and working with revisions.
Obtained via AiClient.agent().
Example::
agent = squid.ai().agent("my-agent")
response = await agent.ask("What is the weather?", options={"temperature": 0.7})
await agent.update_instructions("Always respond in haiku format.")
162 async def ask( 163 self, 164 prompt: str, 165 options: AiChatOptions | None = None, 166 ) -> str: 167 """Ask the agent a question and get a text response. 168 169 Args: 170 prompt: The user's question or instruction. 171 options: Chat options controlling model, temperature, memory, 172 functions, guardrails, and more. See :class:`AiChatOptions`. 173 174 Returns: 175 The agent's response as a string. 176 177 Raises: 178 SquidHttpError: If the agent is not found or the request fails. 179 180 Example:: 181 182 response = await agent.ask( 183 "Summarize this document", 184 options={ 185 "model": "gemini-3-flash", 186 "temperature": 0.3, 187 "memoryOptions": {"memoryId": "session-1", "memoryMode": "read-write"}, 188 }, 189 ) 190 """ 191 result = await self._http.post( 192 "squid-api/v1/ai/agent/ask", 193 {"agentId": self._agent_id, "prompt": prompt, "options": options or {}}, 194 ) 195 return result.get("responseString", "") if result else ""
Ask the agent a question and get a text response.
Arguments:
- prompt: The user's question or instruction.
- options: Chat options controlling model, temperature, memory,
functions, guardrails, and more. See
AiChatOptions.
Returns:
The agent's response as a string.
Raises:
- SquidHttpError: If the agent is not found or the request fails.
Example::
response = await agent.ask(
"Summarize this document",
options={
"model": "gemini-3-flash",
"temperature": 0.3,
"memoryOptions": {"memoryId": "session-1", "memoryMode": "read-write"},
},
)
197 async def ask_with_annotations( 198 self, 199 prompt: str, 200 options: AiChatOptions | None = None, 201 ) -> dict: 202 """Ask the agent and get a response with annotations. 203 204 Annotations include file references, citations, and other metadata 205 the agent may attach to its response. 206 207 Args: 208 prompt: The user's question or instruction. 209 options: Chat options. See :class:`AiChatOptions`. 210 211 Returns: 212 A dict with: 213 - ``responseString`` (str): The text response. 214 - ``annotations`` (dict): Annotation metadata keyed by ID. 215 216 Example:: 217 218 result = await agent.ask_with_annotations("Find relevant docs") 219 print(result["responseString"]) 220 for ann_id, ann in result.get("annotations", {}).items(): 221 print(f" Annotation: {ann}") 222 """ 223 return await self._http.post( 224 "squid-api/v1/ai/agent/askWithAnnotations", 225 {"agentId": self._agent_id, "prompt": prompt, "options": options or {}}, 226 )
Ask the agent and get a response with annotations.
Annotations include file references, citations, and other metadata the agent may attach to its response.
Arguments:
- prompt: The user's question or instruction.
- options: Chat options. See
AiChatOptions.
Returns:
A dict with: -
responseString(str): The text response. -annotations(dict): Annotation metadata keyed by ID.
Example::
result = await agent.ask_with_annotations("Find relevant docs")
print(result["responseString"])
for ann_id, ann in result.get("annotations", {}).items():
print(f" Annotation: {ann}")
230 async def get(self) -> dict | None: 231 """Get the agent's configuration. 232 233 Returns: 234 An ``AiAgent`` dict with keys: ``id``, ``createdAt``, ``updatedAt``, 235 ``description``, ``isPublic``, ``auditLog``, ``options``, ``apiKey``. 236 Returns ``None`` if the agent does not exist. 237 """ 238 return await self._http.get(f"squid-api/v1/ai/agent/get/{self._agent_id}")
Get the agent's configuration.
Returns:
An
AiAgentdict with keys:id,createdAt,updatedAt,description,isPublic,auditLog,options,apiKey. ReturnsNoneif the agent does not exist.
240 async def upsert( 241 self, 242 *, 243 description: str | None = None, 244 is_public: bool | None = None, 245 audit_log: bool | None = None, 246 api_key: str | None = None, 247 options: AiChatOptions | None = None, 248 ) -> None: 249 """Create or update the agent. 250 251 If the agent does not exist, it is created. If it exists, the provided 252 fields are updated (fields set to ``None`` are left unchanged). 253 254 Args: 255 description: A description of the agent's purpose or capabilities. 256 is_public: Whether the agent is publicly accessible (default ``False``). 257 audit_log: Enable audit logging for the agent's activities. 258 api_key: Optional API key used specifically for this agent. 259 options: Default chat options applied to every request unless 260 overridden per-call. See :class:`AiChatOptions`. 261 262 Example:: 263 264 await agent.upsert( 265 description="Customer support agent", 266 options={"model": "gemini-3-flash", "temperature": 0.5}, 267 ) 268 """ 269 body: dict[str, Any] = {"id": self._agent_id} 270 if description is not None: 271 body["description"] = description 272 if is_public is not None: 273 body["isPublic"] = is_public 274 if audit_log is not None: 275 body["auditLog"] = audit_log 276 if api_key is not None: 277 body["apiKey"] = api_key 278 if options is not None: 279 body["options"] = options 280 await self._http.post("squid-api/v1/ai/agent/upsert", body)
Create or update the agent.
If the agent does not exist, it is created. If it exists, the provided
fields are updated (fields set to None are left unchanged).
Arguments:
- description: A description of the agent's purpose or capabilities.
- is_public: Whether the agent is publicly accessible (default
False). - audit_log: Enable audit logging for the agent's activities.
- api_key: Optional API key used specifically for this agent.
- options: Default chat options applied to every request unless
overridden per-call. See
AiChatOptions.
Example::
await agent.upsert(
description="Customer support agent",
options={"model": "gemini-3-flash", "temperature": 0.5},
)
282 async def delete(self) -> None: 283 """Delete the agent permanently.""" 284 await self._http.post("squid-api/v1/ai/agent/delete", {"agentId": self._agent_id})
Delete the agent permanently.
286 async def update_instructions(self, instructions: str) -> None: 287 """Update the agent's system instructions. 288 289 Args: 290 instructions: The new system prompt / instructions text. 291 """ 292 await self._http.post( 293 "squid-api/v1/ai/agent/updateInstructions", 294 {"agentId": self._agent_id, "instructions": instructions}, 295 )
Update the agent's system instructions.
Arguments:
- instructions: The new system prompt / instructions text.
297 async def update_model(self, model: AiChatModelSelection) -> None: 298 """Update the agent's default LLM model. 299 300 Args: 301 model: A model name string (e.g., ``'gemini-3-flash'``) or an 302 ``IntegrationModelSpec`` dict (``{'integrationId': str, 'model': str}``). 303 """ 304 await self._http.post( 305 "squid-api/v1/ai/agent/updateModel", 306 {"agentId": self._agent_id, "model": model}, 307 )
Update the agent's default LLM model.
Arguments:
- model: A model name string (e.g.,
'gemini-3-flash') or anIntegrationModelSpecdict ({'integrationId': str, 'model': str}).
309 async def update_connected_agents( 310 self, connected_agents: list[AiConnectedAgentMetadata] 311 ) -> None: 312 """Update the list of connected agents. 313 314 Connected agents can be called by this agent during conversations. 315 316 Args: 317 connected_agents: List of ``{'agentId': str, 'description': str}`` dicts. 318 """ 319 await self._http.post( 320 "squid-api/v1/ai/agent/updateConnectedAgents", 321 {"agentId": self._agent_id, "connectedAgents": connected_agents}, 322 )
Update the list of connected agents.
Connected agents can be called by this agent during conversations.
Arguments:
- connected_agents: List of
{'agentId': str, 'description': str}dicts.
324 async def update_guardrails(self, guardrails: GuardrailsOptions) -> None: 325 """Update the agent's guardrail settings. 326 327 Args: 328 guardrails: A :class:`GuardrailsOptions` dict with optional keys: 329 ``custom``, ``disablePii``, ``professionalTone``, 330 ``offTopicAnswers``, ``disableProfanity``. 331 332 Example:: 333 334 await agent.update_guardrails( 335 { 336 "professionalTone": True, 337 "disableProfanity": True, 338 } 339 ) 340 """ 341 await self._http.post( 342 "squid-api/v1/ai/agent/updateGuardrails", 343 {"agentId": self._agent_id, "guardrails": guardrails}, 344 )
Update the agent's guardrail settings.
Arguments:
- guardrails: A
GuardrailsOptionsdict with optional keys:custom,disablePii,professionalTone,offTopicAnswers,disableProfanity.
Example::
await agent.update_guardrails(
{
"professionalTone": True,
"disableProfanity": True,
}
)
346 async def update_custom_guardrails(self, custom_guardrail: str) -> None: 347 """Update the custom guardrail instruction text. 348 349 Args: 350 custom_guardrail: Free-form guardrail instruction string. 351 """ 352 await self._http.post( 353 "squid-api/v1/ai/agent/updateCustomGuardrails", 354 {"agentId": self._agent_id, "customGuardrail": custom_guardrail}, 355 )
Update the custom guardrail instruction text.
Arguments:
- custom_guardrail: Free-form guardrail instruction string.
357 async def delete_custom_guardrails(self) -> None: 358 """Delete the custom guardrail, reverting to defaults.""" 359 await self._http.post( 360 "squid-api/v1/ai/agent/deleteCustomGuardrails", 361 {"agentId": self._agent_id}, 362 )
Delete the custom guardrail, reverting to defaults.
366 async def list_revisions(self) -> list[dict]: 367 """List all revisions of this agent. 368 369 Returns: 370 A list of ``AiAgentRevision`` dicts, each containing: 371 ``agentId``, ``revisionNumber``, ``action``, ``createdAt``, 372 ``agentSnapshot``. 373 """ 374 result = await self._http.get(f"squid-api/v1/ai/agent/revisions/{self._agent_id}") 375 return result.get("revisions", []) if result else []
List all revisions of this agent.
Returns:
A list of
AiAgentRevisiondicts, each containing:agentId,revisionNumber,action,createdAt,agentSnapshot.
377 async def restore_revision(self, revision_number: int) -> None: 378 """Restore the agent to a previous revision. 379 380 Args: 381 revision_number: The revision number to restore. 382 """ 383 await self._http.post( 384 "squid-api/v1/ai/agent/restoreRevision", 385 {"agentId": self._agent_id, "revisionNumber": revision_number}, 386 )
Restore the agent to a previous revision.
Arguments:
- revision_number: The revision number to restore.
388 async def delete_revision(self, revision_number: int) -> None: 389 """Delete a specific revision. 390 391 Args: 392 revision_number: The revision number to delete. 393 """ 394 await self._http.post( 395 "squid-api/v1/ai/agent/deleteRevision", 396 {"agentId": self._agent_id, "revisionNumber": revision_number}, 397 )
Delete a specific revision.
Arguments:
- revision_number: The revision number to delete.
354class AiAgent(TypedDict, total=False): 355 """A definition of an AI agent with its properties and default chat options. 356 357 Returned by :meth:`AiClient.list_agents`. 358 """ 359 360 id: str 361 """The unique identifier of the AI agent. Required.""" 362 createdAt: str 363 """ISO 8601 timestamp of when the agent was created. Required.""" 364 updatedAt: str 365 """ISO 8601 timestamp of when the agent was last updated. Required.""" 366 description: str 367 """An optional description of the agent's purpose or capabilities.""" 368 isPublic: bool 369 """Whether the agent is publicly accessible; defaults to False.""" 370 auditLog: bool 371 """Whether audit logging is enabled for the agent's activities; defaults to False.""" 372 options: AiChatOptions 373 """The agent's default chat options, overridable by the user during use. Required.""" 374 apiKey: str 375 """Optional API key used specifically for operations on this agent."""
A definition of an AI agent with its properties and default chat options.
Returned by AiClient.list_agents().
The agent's default chat options, overridable by the user during use. Required.
141class AiAgentExecutionPlanOptions(TypedDict, total=False): 142 """Options for AI agent execution plan.""" 143 144 enabled: bool
Options for AI agent execution plan.
67class AiAgentMemoryOptions(TypedDict, total=False): 68 """Memory/session configuration for agent chat.""" 69 70 memoryId: str 71 """Unique memory ID. Reuse to continue a conversation.""" 72 memoryMode: AiMemoryMode 73 """How memory is used: 'read-write', 'read-only', 'write-only', 'disabled'."""
Memory/session configuration for agent chat.
162class AiAudioCreateSpeechOptions(TypedDict, total=False): 163 """Options for text-to-speech.""" 164 165 modelName: str 166 """'tts-1' or 'tts-1-hd'.""" 167 voice: str 168 """'alloy'|'ash'|'ballad'|'coral'|'echo'|'fable'|'onyx'|'nova'|'sage'|'shimmer'|'verse'.""" 169 responseFormat: str 170 """Audio output format.""" 171 instructions: str 172 """Extra instructions for speech generation.""" 173 speed: float 174 """Speech speed."""
Options for text-to-speech.
177class AiChatOptions(TypedDict, total=False): 178 """Full chat options for AI agent ask/chat operations. 179 180 Mirrors BaseAiChatOptions from the TypeScript SDK. 181 All fields are optional. 182 """ 183 184 model: AiChatModelSelection 185 """LLM model to use. String name or IntegrationModelSpec.""" 186 maxTokens: int 187 """Max input tokens for the AI model.""" 188 maxOutputTokens: int 189 """Max output tokens from the AI model.""" 190 temperature: float 191 """Sampling temperature (default 0.5).""" 192 instructions: str 193 """Extra instructions to include with the prompt.""" 194 functions: list[str] 195 """AI function IDs to expose to the agent.""" 196 memoryOptions: AiAgentMemoryOptions 197 """Memory/session configuration.""" 198 responseFormat: AiAgentResponseFormat 199 """Response format: 'text', 'json_object', or structured output.""" 200 includeReference: bool 201 """Include source references from context.""" 202 smoothTyping: bool 203 """Smooth typing effect for UI display (default true).""" 204 disableContext: bool 205 """Disable the whole context for this request.""" 206 enablePromptRewriteForRag: bool 207 """Rewrite prompt for RAG (default false).""" 208 agentContext: dict[str, Any] 209 """Global context passed to agent and all AI functions.""" 210 connectedAgents: list[AiConnectedAgentMetadata] 211 """Connected agents that can be called.""" 212 connectedIntegrations: list[AiConnectedIntegrationMetadata] 213 """Connected integrations.""" 214 connectedKnowledgeBases: list[AiConnectedKnowledgeBaseMetadata] 215 """Connected knowledge bases.""" 216 guardrails: GuardrailsOptions 217 """Guardrail options.""" 218 contextMetadataFilterForKnowledgeBase: dict[str, Any] 219 """Metadata filters per knowledge base ID.""" 220 voiceOptions: AiAudioCreateSpeechOptions 221 """Options for voice response.""" 222 quotas: AiChatPromptQuotas 223 """Budget for nested AI calls.""" 224 executionPlanOptions: AiAgentExecutionPlanOptions 225 """Execution plan options.""" 226 fileUrls: list[AiFileUrl] 227 """File URLs to include in context.""" 228 fileIds: list[str] 229 """File IDs from AI provider's Files API.""" 230 reasoningEffort: AiReasoningEffort 231 """Reasoning effort level.""" 232 verbosity: AiVerbosityLevel 233 """Response verbosity level.""" 234 useCodeInterpreter: Literal["none", "llm"] 235 """Enable LLM's built-in code interpreter.""" 236 rerankProvider: AiRerankProvider 237 """Reranker provider for context (default 'cohere').""" 238 includeMetadata: bool 239 """Include metadata in context (deprecated).""" 240 timeoutMs: int 241 """Request timeout in milliseconds (default 240000)."""
Full chat options for AI agent ask/chat operations.
Mirrors BaseAiChatOptions from the TypeScript SDK. All fields are optional.
Response format: 'text', 'json_object', or structured output.
135class AiChatPromptQuotas(TypedDict, total=False): 136 """Budget for nested/recursive AI chat calls.""" 137 138 maxNestedCalls: int
Budget for nested/recursive AI chat calls.
32class AiClient: 33 """Entry point for AI operations: agents, knowledge base, audio, image. 34 35 Obtained via :meth:`Squid.ai()`. 36 37 Example:: 38 39 ai = squid.ai() 40 agent = ai.agent("my-agent") 41 kb = ai.knowledge_base("my-kb") 42 image_url = await ai.image().generate("a cat in space") 43 """ 44 45 def __init__(self, http: HttpTransport) -> None: 46 self._http = http 47 48 def agent(self, agent_id: str) -> AgentClient: 49 """Get a client for a specific AI agent. 50 51 Args: 52 agent_id: The unique agent identifier. 53 54 Returns: 55 An :class:`AgentClient` bound to the given agent ID. 56 """ 57 return AgentClient(self._http, agent_id) 58 59 def knowledge_base(self, knowledge_base_id: str) -> KnowledgeBaseClient: 60 """Get a client for a specific knowledge base. 61 62 Args: 63 knowledge_base_id: The unique knowledge base identifier. 64 65 Returns: 66 A :class:`KnowledgeBaseClient` bound to the given knowledge base ID. 67 """ 68 return KnowledgeBaseClient(self._http, knowledge_base_id) 69 70 def image(self) -> ImageClient: 71 """Get a client for image generation and processing. 72 73 Returns: 74 An :class:`ImageClient` instance. 75 """ 76 return ImageClient(self._http) 77 78 def audio(self) -> AudioClient: 79 """Get a client for audio transcription and speech synthesis. 80 81 Returns: 82 An :class:`AudioClient` instance. 83 """ 84 return AudioClient(self._http) 85 86 async def list_agents(self) -> list[AiAgent]: 87 """List all AI agents defined for the application. 88 89 Returns: 90 A list of ``AiAgent`` dicts. Empty list if no agents are defined. 91 """ 92 result = await self._http.get("squid-api/v1/ai/agent/listAgents") 93 return result.get("agents", []) if result else [] 94 95 async def list_knowledge_bases(self) -> list[AiKnowledgeBase]: 96 """List all AI knowledge bases defined for the application. 97 98 Returns: 99 A list of ``AiKnowledgeBase`` dicts. Empty list if no knowledge 100 bases are defined. 101 """ 102 result = await self._http.get("squid-api/v1/ai/knowledge-base/listKnowledgeBases") 103 return result.get("knowledgeBases", []) if result else [] 104 105 async def list_chat_models(self, include_deprecated: bool = False) -> list[ModelIdSpec]: 106 """List all AI chat models available to the application. 107 108 Includes both Squid-provided vendor models and any custom integration 109 models configured for the app. 110 111 Args: 112 include_deprecated: When True, deprecated vendor models are 113 included and marked with ``replacedBy``. Defaults to False. 114 115 Returns: 116 A list of ``ModelIdSpec`` dicts, each with ``modelId``, an optional 117 ``integrationId``, and a human-readable ``displayName``. Vendor 118 models also carry a ``description``, and deprecated vendor models a 119 ``replacedBy`` with the active model their calls are routed to. 120 """ 121 params = {"includeDeprecated": "true"} if include_deprecated else None 122 result = await self._http.get("squid-api/v1/ai/settings/listChatModels", params=params) 123 return result.get("models", []) if result else [] 124 125 async def list_functions(self) -> list[AiFunctionMetadata]: 126 """List all AI functions registered for the application's deployed bundle. 127 128 Returns: 129 A list of ``AiFunctionMetadata`` dicts. Empty list if no functions 130 are registered. 131 """ 132 result = await self._http.get("squid-api/v1/ai/function/listFunctions") 133 return result.get("functions", []) if result else []
Entry point for AI operations: agents, knowledge base, audio, image.
Obtained via Squid.ai()().
Example::
ai = squid.ai()
agent = ai.agent("my-agent")
kb = ai.knowledge_base("my-kb")
image_url = await ai.image().generate("a cat in space")
48 def agent(self, agent_id: str) -> AgentClient: 49 """Get a client for a specific AI agent. 50 51 Args: 52 agent_id: The unique agent identifier. 53 54 Returns: 55 An :class:`AgentClient` bound to the given agent ID. 56 """ 57 return AgentClient(self._http, agent_id)
Get a client for a specific AI agent.
Arguments:
- agent_id: The unique agent identifier.
Returns:
An
AgentClientbound to the given agent ID.
59 def knowledge_base(self, knowledge_base_id: str) -> KnowledgeBaseClient: 60 """Get a client for a specific knowledge base. 61 62 Args: 63 knowledge_base_id: The unique knowledge base identifier. 64 65 Returns: 66 A :class:`KnowledgeBaseClient` bound to the given knowledge base ID. 67 """ 68 return KnowledgeBaseClient(self._http, knowledge_base_id)
Get a client for a specific knowledge base.
Arguments:
- knowledge_base_id: The unique knowledge base identifier.
Returns:
A
KnowledgeBaseClientbound to the given knowledge base ID.
86 async def list_agents(self) -> list[AiAgent]: 87 """List all AI agents defined for the application. 88 89 Returns: 90 A list of ``AiAgent`` dicts. Empty list if no agents are defined. 91 """ 92 result = await self._http.get("squid-api/v1/ai/agent/listAgents") 93 return result.get("agents", []) if result else []
List all AI agents defined for the application.
Returns:
A list of
AiAgentdicts. Empty list if no agents are defined.
95 async def list_knowledge_bases(self) -> list[AiKnowledgeBase]: 96 """List all AI knowledge bases defined for the application. 97 98 Returns: 99 A list of ``AiKnowledgeBase`` dicts. Empty list if no knowledge 100 bases are defined. 101 """ 102 result = await self._http.get("squid-api/v1/ai/knowledge-base/listKnowledgeBases") 103 return result.get("knowledgeBases", []) if result else []
List all AI knowledge bases defined for the application.
Returns:
A list of
AiKnowledgeBasedicts. Empty list if no knowledge bases are defined.
105 async def list_chat_models(self, include_deprecated: bool = False) -> list[ModelIdSpec]: 106 """List all AI chat models available to the application. 107 108 Includes both Squid-provided vendor models and any custom integration 109 models configured for the app. 110 111 Args: 112 include_deprecated: When True, deprecated vendor models are 113 included and marked with ``replacedBy``. Defaults to False. 114 115 Returns: 116 A list of ``ModelIdSpec`` dicts, each with ``modelId``, an optional 117 ``integrationId``, and a human-readable ``displayName``. Vendor 118 models also carry a ``description``, and deprecated vendor models a 119 ``replacedBy`` with the active model their calls are routed to. 120 """ 121 params = {"includeDeprecated": "true"} if include_deprecated else None 122 result = await self._http.get("squid-api/v1/ai/settings/listChatModels", params=params) 123 return result.get("models", []) if result else []
List all AI chat models available to the application.
Includes both Squid-provided vendor models and any custom integration models configured for the app.
Arguments:
- include_deprecated: When True, deprecated vendor models are
included and marked with
replacedBy. Defaults to False.
Returns:
A list of
ModelIdSpecdicts, each withmodelId, an optionalintegrationId, and a human-readabledisplayName. Vendor models also carry adescription, and deprecated vendor models areplacedBywith the active model their calls are routed to.
125 async def list_functions(self) -> list[AiFunctionMetadata]: 126 """List all AI functions registered for the application's deployed bundle. 127 128 Returns: 129 A list of ``AiFunctionMetadata`` dicts. Empty list if no functions 130 are registered. 131 """ 132 result = await self._http.get("squid-api/v1/ai/function/listFunctions") 133 return result.get("functions", []) if result else []
List all AI functions registered for the application's deployed bundle.
Returns:
A list of
AiFunctionMetadatadicts. Empty list if no functions are registered.
76class AiConnectedAgentMetadata(TypedDict): 77 """Metadata for a connected agent.""" 78 79 agentId: str 80 description: str
Metadata for a connected agent.
83class AiConnectedIntegrationMetadata(TypedDict, total=False): 84 """Metadata for a connected integration. 85 86 ``integrationId`` and ``integrationType`` are required by the platform API; 87 the remaining fields are optional. 88 """ 89 90 integrationId: str 91 """The ID of the connected integration. Required.""" 92 integrationType: str 93 """The integration type, e.g. 'hubspot', 'slack', 'api'. Required.""" 94 description: str 95 """Optional description used as the AI function description for the parent agent.""" 96 instructions: str 97 """Optional instructions for the connected integration agent, overriding the default.""" 98 functionsToUse: list[str] 99 """AI function IDs the agent may use. Omit for all functions; [] for none.""" 100 options: dict[str, Any] 101 """Additional integration options interpreted by Squid Core or connector AI functions.""" 102 connectedAsMcp: bool 103 """Treat this integration as an MCP server (API integrations with exposeAsMcpServer)."""
Metadata for a connected integration.
integrationId and integrationType are required by the platform API;
the remaining fields are optional.
Optional instructions for the connected integration agent, overriding the default.
106class AiConnectedKnowledgeBaseMetadata(TypedDict, total=False): 107 """Metadata for a connected knowledge base.""" 108 109 knowledgeBaseId: str 110 description: str 111 includeMetadata: bool
Metadata for a connected knowledge base.
450class AiContextFileOptions(TypedDict, total=False): 451 """Options for file context processing.""" 452 453 chunkOverlap: int 454 ragType: str
Options for file context processing.
430class AiContextTextOptions(TypedDict, total=False): 431 """Options for text context processing.""" 432 433 chunkOverlap: int 434 """Amount of chunk overlap in characters.""" 435 ragType: str 436 """The type of RAG to use."""
Options for text context processing.
114class AiFileUrl(TypedDict, total=False): 115 """File URL to include in chat context.""" 116 117 id: str 118 type: str 119 purpose: str 120 url: str 121 description: str 122 fileName: str
File URL to include in chat context.
515class AiFunctionAttributes(TypedDict, total=False): 516 """Additional optional readonly metadata for an AI function.""" 517 518 integrationType: list[str] 519 """Types of integration this function is used for. Functions with a defined 520 'integrationType' require 'integrationId' to be passed as part of the function context."""
Additional optional readonly metadata for an AI function.
523class AiFunctionMetadata(TypedDict, total=False): 524 """Metadata describing an AI function available in the application. 525 526 Returned by :meth:`AiClient.list_functions`. 527 """ 528 529 serviceFunction: str 530 """The fully qualified name of the function ('ServiceName:functionName'). Required.""" 531 description: str 532 """Description of what the function does.""" 533 promptId: str 534 """Opaque ID of a registered prompt that supplies this function's description; 535 resolved server-side.""" 536 params: list[AiFunctionParam] 537 """Parameters that the function accepts. Required.""" 538 attributes: AiFunctionAttributes 539 """Additional attributes for the function.""" 540 categories: list[str] 541 """Categories this function belongs to.""" 542 internal: bool 543 """Whether this function is internal and not meant for direct use."""
Metadata describing an AI function available in the application.
Returned by AiClient.list_functions().
The fully qualified name of the function ('ServiceName:functionName'). Required.
500class AiFunctionParam(TypedDict, total=False): 501 """Defines the structure of a parameter for an AI function.""" 502 503 name: str 504 """Name of the parameter. Required.""" 505 description: str 506 """Description of the parameter's purpose. Required.""" 507 type: AiFunctionParamType 508 """Data type of the parameter. Required.""" 509 required: bool 510 """Indicates if the parameter is mandatory. Required.""" 511 enum: list[str] 512 """List of possible values for the parameter, if applicable."""
Defines the structure of a parameter for an AI function.
405class AiKnowledgeBase(TypedDict, total=False): 406 """An AI knowledge base that can be attached to an AI agent. 407 408 Returned by :meth:`AiClient.list_knowledge_bases`. 409 """ 410 411 id: str 412 """The unique identifier of the knowledge base. Required.""" 413 appId: str 414 """The app ID that the knowledge base belongs to. Required.""" 415 description: str 416 """The user's description of the knowledge base. Required.""" 417 metadataFields: list[AiKnowledgeBaseMetadataField] 418 """Predefined metadata fields that can be used for filtering. Required.""" 419 embeddingModel: AiEmbeddingsModelSelection 420 """The embedding model used by this knowledge base. Required.""" 421 chatModel: AiChatModelSelection 422 """The model used when asking questions of this knowledge base. Required.""" 423 vectorDbType: Literal["postgres", "mongoAtlas"] 424 """The vector store backend the knowledge base reads/writes from. Set at creation 425 and immutable thereafter. Absent on older records.""" 426 updatedAt: str 427 """ISO 8601 timestamp of when the knowledge base was last updated. Required."""
An AI knowledge base that can be attached to an AI agent.
Returned by AiClient.list_knowledge_bases().
Predefined metadata fields that can be used for filtering. Required.
The embedding model used by this knowledge base. Required.
The model used when asking questions of this knowledge base. Required.
381class AiKnowledgeBaseMetadataField(TypedDict, total=False): 382 """Metadata field definition for a knowledge base.""" 383 384 name: str 385 dataType: str 386 required: bool 387 description: str
Metadata field definition for a knowledge base.
288class AiQueryAnalyzeResultsOptions(TypedDict, total=False): 289 """Options for the result-analysis stage of AI query.""" 290 291 disabled: bool 292 """When true, skip analysis and return raw results only.""" 293 enableCodeInterpreter: bool 294 """Enable code interpreter mode (default false).""" 295 aiOptions: AiChatOptions 296 """Customize AI agent behavior used by the stage.""" 297 agentId: AiAgentId 298 """If set, use this agent to analyze results and produce the final answer."""
Options for the result-analysis stage of AI query.
274class AiQueryGenerateQueryOptions(TypedDict, total=False): 275 """Options for the query-generation stage of AI query.""" 276 277 aiOptions: AiChatOptions 278 """Customize AI agent behavior used by the stage.""" 279 maxErrorCorrections: int 280 """Number of retries due to errors in a generated AI query (default 2).""" 281 agentId: AiAgentId 282 """If set, use this agent to generate the query.""" 283 allowClarification: bool 284 """When true, allow the AI to ask a clarifying question instead of 285 generating a query for ambiguous prompts (default false)."""
Options for the query-generation stage of AI query.
310class AiQueryOptions(TypedDict, total=False): 311 """Options for configuring AI query execution. 312 313 Mirrors ``AiQueryOptions`` from the TypeScript SDK. All fields optional. 314 """ 315 316 instructions: str 317 """Custom instructions applied to all stages unless overridden per-stage.""" 318 enableRawResults: bool 319 """Enable raw results output.""" 320 selectCollectionsOptions: AiQuerySelectCollectionsOptions 321 """Collection-selection stage options.""" 322 generateQueryOptions: AiQueryGenerateQueryOptions 323 """Query-generation stage options.""" 324 analyzeResultsOptions: AiQueryAnalyzeResultsOptions 325 """Result-analysis stage options.""" 326 sessionContext: AiSessionContext 327 """Session information (``agentId`` may be omitted).""" 328 memoryOptions: AiAgentMemoryOptions 329 """Memory/session configuration.""" 330 generateQueriesOnly: bool 331 """If true, return generated queries without executing or analyzing them.""" 332 validateWithAiOptions: AiQueryValidateWithAiOptions 333 """Optional AI validation of generated queries."""
Options for configuring AI query execution.
Mirrors AiQueryOptions from the TypeScript SDK. All fields optional.
263class AiQuerySelectCollectionsOptions(TypedDict, total=False): 264 """Options for the collection-selection stage of AI query.""" 265 266 collectionsToUse: list[str] 267 """Restrict query to these collections. Defaults to all collections.""" 268 runMode: AiQueryCollectionsSelectionRunMode 269 """Stage behavior: 'default', 'force', or 'disable'.""" 270 aiOptions: AiChatOptions 271 """Customize AI agent behavior used by the stage."""
Options for the collection-selection stage of AI query.
301class AiQueryValidateWithAiOptions(TypedDict, total=False): 302 """Options for AI-based validation of generated queries.""" 303 304 enabled: bool 305 """Whether AI validation is enabled.""" 306 aiOptions: AiChatOptions 307 """Defaults to the same model used for query generation."""
Options for AI-based validation of generated queries.
250class AiSessionContext(TypedDict, total=False): 251 """Session context for AI query execution. 252 253 Mirrors the TypeScript ``AiSessionContext`` type. All fields optional 254 here because the query endpoint accepts a partial context (``agentId`` 255 may be omitted). 256 """ 257 258 clientId: str 259 agentId: str 260 jobId: str
Session context for AI query execution.
Mirrors the TypeScript AiSessionContext type. All fields optional
here because the query endpoint accepts a partial context (agentId
may be omitted).
125class AiStructuredOutputFormat(TypedDict): 126 """Structured output format for JSON responses.""" 127 128 type: Literal["json_schema"] 129 schema: dict[str, Any]
Structured output format for JSON responses.
718class AudioClient: 719 """Audio transcription and speech synthesis. 720 721 Obtained via :meth:`AiClient.audio`. 722 723 Example:: 724 725 text = await squid.ai().audio().transcribe(audio_bytes) 726 speech = await squid.ai().audio().create_speech("Hello!", options={"voice": "nova"}) 727 """ 728 729 def __init__(self, http: HttpTransport) -> None: 730 self._http = http 731 732 async def transcribe( 733 self, 734 audio_data: bytes, 735 filename: str = "audio.wav", 736 content_type: str = "audio/wav", 737 *, 738 options: dict[str, Any] | None = None, 739 ) -> str: 740 """Transcribe audio to text. 741 742 Args: 743 audio_data: The audio file content as bytes. 744 filename: The filename (used in the multipart upload). 745 content_type: The MIME type of the audio file. 746 options: Provider-specific transcription options. 747 748 Returns: 749 The transcribed text. 750 """ 751 form_data: dict[str, str] = { 752 "optionsJson": json.dumps(options or {}), 753 } 754 result = await self._http.post_form( 755 "squid-api/v1/ai/audio/transcribe", 756 data=form_data, 757 files=[("file", (filename, audio_data, content_type))], 758 ) 759 return result if isinstance(result, str) else str(result) 760 761 async def create_speech( 762 self, 763 text: str, 764 options: AiAudioCreateSpeechOptions, 765 ) -> bytes: 766 """Generate speech audio from text. 767 768 Args: 769 text: The text to convert to speech. 770 options: Speech generation options. See :class:`AiAudioCreateSpeechOptions`. 771 Required keys: ``modelName`` (e.g., ``'tts-1'``), ``voice`` 772 (e.g., ``'nova'``, ``'alloy'``). 773 774 Returns: 775 Raw audio file bytes (e.g., MP3 format by default). 776 777 Example:: 778 779 audio_data = ( 780 await squid.ai() 781 .audio() 782 .create_speech( 783 "Hello!", 784 options={ 785 "modelName": "tts-1", 786 "voice": "nova", 787 }, 788 ) 789 ) 790 with open("speech.mp3", "wb") as f: 791 f.write(audio_data) 792 """ 793 return await self._http.post( 794 "squid-api/v1/ai/audio/createSpeech", 795 {"input": text, "options": options}, 796 )
Audio transcription and speech synthesis.
Obtained via AiClient.audio().
Example::
text = await squid.ai().audio().transcribe(audio_bytes)
speech = await squid.ai().audio().create_speech("Hello!", options={"voice": "nova"})
732 async def transcribe( 733 self, 734 audio_data: bytes, 735 filename: str = "audio.wav", 736 content_type: str = "audio/wav", 737 *, 738 options: dict[str, Any] | None = None, 739 ) -> str: 740 """Transcribe audio to text. 741 742 Args: 743 audio_data: The audio file content as bytes. 744 filename: The filename (used in the multipart upload). 745 content_type: The MIME type of the audio file. 746 options: Provider-specific transcription options. 747 748 Returns: 749 The transcribed text. 750 """ 751 form_data: dict[str, str] = { 752 "optionsJson": json.dumps(options or {}), 753 } 754 result = await self._http.post_form( 755 "squid-api/v1/ai/audio/transcribe", 756 data=form_data, 757 files=[("file", (filename, audio_data, content_type))], 758 ) 759 return result if isinstance(result, str) else str(result)
Transcribe audio to text.
Arguments:
- audio_data: The audio file content as bytes.
- filename: The filename (used in the multipart upload).
- content_type: The MIME type of the audio file.
- options: Provider-specific transcription options.
Returns:
The transcribed text.
761 async def create_speech( 762 self, 763 text: str, 764 options: AiAudioCreateSpeechOptions, 765 ) -> bytes: 766 """Generate speech audio from text. 767 768 Args: 769 text: The text to convert to speech. 770 options: Speech generation options. See :class:`AiAudioCreateSpeechOptions`. 771 Required keys: ``modelName`` (e.g., ``'tts-1'``), ``voice`` 772 (e.g., ``'nova'``, ``'alloy'``). 773 774 Returns: 775 Raw audio file bytes (e.g., MP3 format by default). 776 777 Example:: 778 779 audio_data = ( 780 await squid.ai() 781 .audio() 782 .create_speech( 783 "Hello!", 784 options={ 785 "modelName": "tts-1", 786 "voice": "nova", 787 }, 788 ) 789 ) 790 with open("speech.mp3", "wb") as f: 791 f.write(audio_data) 792 """ 793 return await self._http.post( 794 "squid-api/v1/ai/audio/createSpeech", 795 {"input": text, "options": options}, 796 )
Generate speech audio from text.
Arguments:
- text: The text to convert to speech.
- options: Speech generation options. See
AiAudioCreateSpeechOptions. Required keys:modelName(e.g.,'tts-1'),voice(e.g.,'nova','alloy').
Returns:
Raw audio file bytes (e.g., MP3 format by default).
Example::
audio_data = (
await squid.ai()
.audio()
.create_speech(
"Hello!",
options={
"modelName": "tts-1",
"voice": "nova",
},
)
)
with open("speech.mp3", "wb") as f:
f.write(audio_data)
652class CreatePdfDimensionsOptions(TypedDict): 653 """PDF output options by custom dimensions.""" 654 655 type: Literal["dimensions"] 656 width: int 657 """Width in pixels.""" 658 height: int 659 """Height in pixels."""
PDF output options by custom dimensions.
633class CreatePdfFormatOptions(TypedDict): 634 """PDF output options by format.""" 635 636 type: Literal["format"] 637 format: Literal[ 638 "letter", 639 "legal", 640 "tabloid", 641 "ledger", 642 "a0", 643 "a1", 644 "a2", 645 "a3", 646 "a4", 647 "a5", 648 "a6", 649 ]
PDF output options by format.
665class ExtractDataFromDocumentOptions(TypedDict, total=False): 666 """Options for document data extraction.""" 667 668 extractImages: bool 669 """Whether to extract embedded images.""" 670 imageMinSizePixels: int 671 """Minimum image size to extract.""" 672 pageIndexes: list[int] 673 """Specific pages to extract (0-based).""" 674 preferredExtractionMethod: str 675 discardOriginalFile: bool
Options for document data extraction.
17class ExtractionClient: 18 """Document extraction and PDF creation.""" 19 20 def __init__(self, http: HttpTransport) -> None: 21 self._http = http 22 23 async def create_pdf_from_html( 24 self, 25 inner_html: str, 26 *, 27 title: str | None = None, 28 css_url: str | None = None, 29 output_options: CreatePdfOutputOptions | None = None, 30 ) -> dict: 31 """Create a PDF from HTML content. 32 33 Returns CreatePdfResponse with 'url' and 'fileName'. 34 """ 35 body: dict[str, Any] = {"type": "html", "innerHtml": inner_html} 36 if title is not None: 37 body["title"] = title 38 if css_url is not None: 39 body["cssUrl"] = css_url 40 if output_options is not None: 41 body["outputOptions"] = output_options 42 return await self._http.post("squid-api/v1/extraction/createPdf", body) 43 44 async def create_pdf_from_url( 45 self, 46 url: str, 47 *, 48 title: str | None = None, 49 output_options: CreatePdfOutputOptions | None = None, 50 ) -> dict: 51 """Create a PDF from a URL. 52 53 Returns CreatePdfResponse with 'url' and 'fileName'. 54 """ 55 body: dict[str, Any] = {"type": "url", "url": url} 56 if title is not None: 57 body["title"] = title 58 if output_options is not None: 59 body["outputOptions"] = output_options 60 return await self._http.post("squid-api/v1/extraction/createPdf", body) 61 62 async def extract_data_from_document_url( 63 self, 64 url: str, 65 options: ExtractDataFromDocumentOptions | None = None, 66 ) -> dict: 67 """Extract structured data from a document URL. 68 69 Returns ExtractDataFromDocumentResponse with 'pages' and optional 'longTermStoragePath'. 70 """ 71 body: dict[str, Any] = {"url": url} 72 if options is not None: 73 body["options"] = options 74 return await self._http.post("squid-api/v1/extraction/extractDataFromDocumentUrl", body) 75 76 async def extract_data_from_document_file( 77 self, 78 file_data: bytes, 79 filename: str, 80 content_type: str = "application/pdf", 81 options: ExtractDataFromDocumentOptions | None = None, 82 ) -> dict: 83 """Extract structured data from a document file. 84 85 Returns ExtractDataFromDocumentResponse with 'pages' and optional 'longTermStoragePath'. 86 """ 87 request: dict[str, Any] = {} 88 if options is not None: 89 request["options"] = options 90 form_data = {"request": json.dumps(request)} 91 92 return await self._http.post_form( 93 "squid-api/v1/extraction/extractDataFromDocumentFile", 94 data=form_data, 95 files=[("file", (filename, file_data, content_type))], 96 )
Document extraction and PDF creation.
23 async def create_pdf_from_html( 24 self, 25 inner_html: str, 26 *, 27 title: str | None = None, 28 css_url: str | None = None, 29 output_options: CreatePdfOutputOptions | None = None, 30 ) -> dict: 31 """Create a PDF from HTML content. 32 33 Returns CreatePdfResponse with 'url' and 'fileName'. 34 """ 35 body: dict[str, Any] = {"type": "html", "innerHtml": inner_html} 36 if title is not None: 37 body["title"] = title 38 if css_url is not None: 39 body["cssUrl"] = css_url 40 if output_options is not None: 41 body["outputOptions"] = output_options 42 return await self._http.post("squid-api/v1/extraction/createPdf", body)
Create a PDF from HTML content.
Returns CreatePdfResponse with 'url' and 'fileName'.
44 async def create_pdf_from_url( 45 self, 46 url: str, 47 *, 48 title: str | None = None, 49 output_options: CreatePdfOutputOptions | None = None, 50 ) -> dict: 51 """Create a PDF from a URL. 52 53 Returns CreatePdfResponse with 'url' and 'fileName'. 54 """ 55 body: dict[str, Any] = {"type": "url", "url": url} 56 if title is not None: 57 body["title"] = title 58 if output_options is not None: 59 body["outputOptions"] = output_options 60 return await self._http.post("squid-api/v1/extraction/createPdf", body)
Create a PDF from a URL.
Returns CreatePdfResponse with 'url' and 'fileName'.
62 async def extract_data_from_document_url( 63 self, 64 url: str, 65 options: ExtractDataFromDocumentOptions | None = None, 66 ) -> dict: 67 """Extract structured data from a document URL. 68 69 Returns ExtractDataFromDocumentResponse with 'pages' and optional 'longTermStoragePath'. 70 """ 71 body: dict[str, Any] = {"url": url} 72 if options is not None: 73 body["options"] = options 74 return await self._http.post("squid-api/v1/extraction/extractDataFromDocumentUrl", body)
Extract structured data from a document URL.
Returns ExtractDataFromDocumentResponse with 'pages' and optional 'longTermStoragePath'.
76 async def extract_data_from_document_file( 77 self, 78 file_data: bytes, 79 filename: str, 80 content_type: str = "application/pdf", 81 options: ExtractDataFromDocumentOptions | None = None, 82 ) -> dict: 83 """Extract structured data from a document file. 84 85 Returns ExtractDataFromDocumentResponse with 'pages' and optional 'longTermStoragePath'. 86 """ 87 request: dict[str, Any] = {} 88 if options is not None: 89 request["options"] = options 90 form_data = {"request": json.dumps(request)} 91 92 return await self._http.post_form( 93 "squid-api/v1/extraction/extractDataFromDocumentFile", 94 data=form_data, 95 files=[("file", (filename, file_data, content_type))], 96 )
Extract structured data from a document file.
Returns ExtractDataFromDocumentResponse with 'pages' and optional 'longTermStoragePath'.
457class FileContextRequest(TypedDict, total=False): 458 """Request to upsert a file context.""" 459 460 contextId: str 461 type: Literal["file"] 462 metadata: dict[str, Any] 463 extractImages: bool 464 imageMinSizePixels: int 465 extractionModel: AiChatModelSelection 466 options: AiContextFileOptions 467 preferredExtractionMethod: str 468 discardOriginalFile: bool
Request to upsert a file context.
565class FluxOptions(TypedDict, total=False): 566 """Options for Flux image generation.""" 567 568 modelName: Literal["flux-pro-1.1", "flux-kontext-pro"] 569 width: int 570 """Must be multiple of 32, min 256, max 1440.""" 571 height: int 572 """Must be multiple of 32, min 256, max 1440.""" 573 prompt_upsampling: bool 574 seed: int 575 safety_tolerance: int 576 """1 (strict) to 5 (permissive)."""
Options for Flux image generation.
549class GptImageOptions(TypedDict, total=False): 550 """Options for OpenAI gpt-image-* family image generation.""" 551 552 modelName: Literal[ 553 "gpt-image-1", 554 "gpt-image-1-mini", 555 "gpt-image-1.5", 556 "gpt-image-2", 557 "gpt-image-2-2026-04-21", 558 "chatgpt-image-latest", 559 ] 560 quality: Literal["auto", "high", "medium", "low"] 561 size: Literal["1024x1024", "1024x1536", "1536x1024", "auto"] 562 numberOfImagesToGenerate: int
Options for OpenAI gpt-image-* family image generation.
147class GuardrailsOptions(TypedDict, total=False): 148 """Guardrail options for agent responses.""" 149 150 custom: str 151 """A custom guardrail instruction.""" 152 disablePii: bool 153 """Disables personally identifiable information if true.""" 154 professionalTone: bool 155 """Enforces a professional tone if true.""" 156 offTopicAnswers: bool 157 """Prevents off-topic answers if true.""" 158 disableProfanity: bool 159 """Disables profanity if true."""
Guardrail options for agent responses.
644class ImageClient: 645 """Image generation and processing. 646 647 Supports DALL-E, Stable Diffusion Core, and Flux models. 648 649 Obtained via :meth:`AiClient.image`. 650 651 Example:: 652 653 image_url = ( 654 await squid.ai() 655 .image() 656 .generate( 657 "a cat astronaut on the moon", 658 options={"modelName": "gpt-image-1", "quality": "high"}, 659 ) 660 ) 661 """ 662 663 def __init__(self, http: HttpTransport) -> None: 664 self._http = http 665 666 async def generate( 667 self, 668 prompt: str, 669 options: ImageGenerateOptions | None = None, 670 ) -> str: 671 """Generate an image from a text prompt. 672 673 Args: 674 prompt: A text description of the image to generate. 675 options: Provider-specific generation options. Use one of: 676 - :class:`GptImageOptions`: ``{'modelName': 'gpt-image-1', 'quality': 'high', 'size': '1024x1024'}`` 677 - :class:`FluxOptions`: ``{'modelName': 'flux-pro-1.1', 'width': 1024, 'height': 768}`` 678 - :class:`StableDiffusionOptions`: ``{'modelName': 'stable-diffusion-core', 'aspectRatio': '16:9'}`` 679 680 Returns: 681 The URL of the generated image. 682 """ 683 result = await self._http.post( 684 "squid-api/v1/ai/image/generate", 685 {"prompt": prompt, "options": options or {}}, 686 ) 687 return result if isinstance(result, str) else str(result) 688 689 async def remove_background( 690 self, 691 image_data: bytes, 692 filename: str = "image.png", 693 content_type: str = "image/png", 694 ) -> str: 695 """Remove the background from an image. 696 697 Args: 698 image_data: The image file content as bytes. 699 filename: The filename (used in the multipart upload). 700 content_type: The MIME type of the image. 701 702 Returns: 703 The URL of the processed image with the background removed. 704 """ 705 result = await self._http.post_form( 706 "squid-api/v1/ai/image/removeBackground", 707 data={}, 708 files=[("file", (filename, image_data, content_type))], 709 ) 710 return result if isinstance(result, str) else str(result)
Image generation and processing.
Supports DALL-E, Stable Diffusion Core, and Flux models.
Obtained via AiClient.image().
Example::
image_url = (
await squid.ai()
.image()
.generate(
"a cat astronaut on the moon",
options={"modelName": "gpt-image-1", "quality": "high"},
)
)
666 async def generate( 667 self, 668 prompt: str, 669 options: ImageGenerateOptions | None = None, 670 ) -> str: 671 """Generate an image from a text prompt. 672 673 Args: 674 prompt: A text description of the image to generate. 675 options: Provider-specific generation options. Use one of: 676 - :class:`GptImageOptions`: ``{'modelName': 'gpt-image-1', 'quality': 'high', 'size': '1024x1024'}`` 677 - :class:`FluxOptions`: ``{'modelName': 'flux-pro-1.1', 'width': 1024, 'height': 768}`` 678 - :class:`StableDiffusionOptions`: ``{'modelName': 'stable-diffusion-core', 'aspectRatio': '16:9'}`` 679 680 Returns: 681 The URL of the generated image. 682 """ 683 result = await self._http.post( 684 "squid-api/v1/ai/image/generate", 685 {"prompt": prompt, "options": options or {}}, 686 ) 687 return result if isinstance(result, str) else str(result)
Generate an image from a text prompt.
Arguments:
- prompt: A text description of the image to generate.
- options: Provider-specific generation options. Use one of:
GptImageOptions:{'modelName': 'gpt-image-1', 'quality': 'high', 'size': '1024x1024'}FluxOptions:{'modelName': 'flux-pro-1.1', 'width': 1024, 'height': 768}StableDiffusionOptions:{'modelName': 'stable-diffusion-core', 'aspectRatio': '16:9'}
Returns:
The URL of the generated image.
689 async def remove_background( 690 self, 691 image_data: bytes, 692 filename: str = "image.png", 693 content_type: str = "image/png", 694 ) -> str: 695 """Remove the background from an image. 696 697 Args: 698 image_data: The image file content as bytes. 699 filename: The filename (used in the multipart upload). 700 content_type: The MIME type of the image. 701 702 Returns: 703 The URL of the processed image with the background removed. 704 """ 705 result = await self._http.post_form( 706 "squid-api/v1/ai/image/removeBackground", 707 data={}, 708 files=[("file", (filename, image_data, content_type))], 709 ) 710 return result if isinstance(result, str) else str(result)
Remove the background from an image.
Arguments:
- image_data: The image file content as bytes.
- filename: The filename (used in the multipart upload).
- content_type: The MIME type of the image.
Returns:
The URL of the processed image with the background removed.
390class IntegrationEmbeddingModelSpec(TypedDict): 391 """Specifies an embedding model from a specific integration.""" 392 393 integrationId: str 394 """The ID of the integration providing the embedding model.""" 395 model: str 396 """The model name as recognized by the provider.""" 397 dimensions: int 398 """The number of dimensions in the embedding vector output."""
Specifies an embedding model from a specific integration.
30class IntegrationModelSpec(TypedDict): 31 """Specifies a model from a specific integration.""" 32 33 integrationId: str 34 model: str
Specifies a model from a specific integration.
405class KnowledgeBaseClient: 406 """Operations on a single knowledge base. 407 408 Provides methods for managing knowledge base configuration, upserting 409 and searching text/file contexts, and retrieving individual contexts. 410 411 Obtained via :meth:`AiClient.knowledge_base`. 412 413 Example:: 414 415 kb = squid.ai().knowledge_base("my-kb") 416 await kb.upsert(description="Product documentation") 417 await kb.upsert_contexts( 418 [ 419 { 420 "contextId": "doc-1", 421 "type": "text", 422 "title": "Getting Started", 423 "text": "Welcome to our product...", 424 } 425 ] 426 ) 427 results = await kb.search("How do I get started?") 428 """ 429 430 def __init__(self, http: HttpTransport, kb_id: str) -> None: 431 self._http = http 432 self._kb_id = kb_id 433 434 async def get(self) -> dict | None: 435 """Get the knowledge base details. 436 437 Returns: 438 An ``AiKnowledgeBase`` dict with keys: ``id``, ``appId``, 439 ``description``, ``metadataFields``, ``embeddingModel``, 440 ``chatModel``, ``updatedAt``. Returns ``None`` if not found. 441 """ 442 return await self._http.get(f"squid-api/v1/ai/knowledge-base/get/{self._kb_id}") 443 444 async def upsert( 445 self, 446 *, 447 description: str | None = None, 448 metadata_fields: list[AiKnowledgeBaseMetadataField] | None = None, 449 embedding_model: str | None = None, 450 chat_model: AiChatModelSelection | None = None, 451 name: str | None = None, 452 ) -> None: 453 """Create or update the knowledge base. 454 455 Args: 456 description: Description of the knowledge base's content. 457 metadata_fields: Schema for metadata fields used in filtering. 458 Each field: ``{'name': str, 'dataType': str, 'required': bool, 'description'?: str}``. 459 embedding_model: The embedding model name for vectorization. 460 chat_model: The LLM model for answering questions over this KB. 461 name: Display name for the knowledge base. 462 """ 463 kb: dict[str, Any] = {"id": self._kb_id} 464 if description is not None: 465 kb["description"] = description 466 if metadata_fields is not None: 467 kb["metadataFields"] = metadata_fields 468 if embedding_model is not None: 469 kb["embeddingModel"] = embedding_model 470 if chat_model is not None: 471 kb["chatModel"] = chat_model 472 if name is not None: 473 kb["name"] = name 474 await self._http.post("squid-api/v1/ai/knowledge-base/upsert", {"knowledgeBase": kb}) 475 476 async def delete(self) -> None: 477 """Delete the knowledge base and all its contexts permanently.""" 478 await self._http.post("squid-api/v1/ai/knowledge-base/delete", {"id": self._kb_id}) 479 480 # --- Contexts --- 481 482 async def get_context(self, context_id: str) -> dict | None: 483 """Get a specific context entry. 484 485 Args: 486 context_id: The unique context identifier. 487 488 Returns: 489 An ``AiKnowledgeBaseContext`` dict with keys: ``id``, ``appId``, 490 ``knowledgeBaseId``, ``createdAt``, ``updatedAt``, ``type``, 491 ``title``, ``text``, ``preview``, ``sizeBytes``, ``metadata``, 492 ``requestConfig``. Returns ``None`` if not found. 493 """ 494 return await self._http.get( 495 f"squid-api/v1/ai/knowledge-base/getContext/{self._kb_id}/{context_id}" 496 ) 497 498 async def list_contexts(self) -> list[dict]: 499 """List all contexts in the knowledge base. 500 501 Deprecated: fetches every context in one call with no pagination — expensive for large 502 knowledge bases. Use :meth:`list_contexts_page` instead, which supports 503 ``offset``/``limit``/``search``. 504 505 Returns: 506 A list of ``AiKnowledgeBaseContext`` dicts. 507 """ 508 result = await self._http.get(f"squid-api/v1/ai/knowledge-base/listContexts/{self._kb_id}") 509 return result.get("contexts", []) if result else [] 510 511 async def list_contexts_page( 512 self, 513 *, 514 offset: int | None = None, 515 limit: int | None = None, 516 search: str | None = None, 517 ) -> dict: 518 """List a page of contexts in the knowledge base. 519 520 Args: 521 offset: The number of contexts to skip, for pagination. 522 limit: The maximum number of contexts to return, for pagination. 523 search: Case-insensitive substring search across id/title only. 524 525 Returns: 526 A dict with ``contexts`` (a list of ``AiKnowledgeBaseContext`` dicts for the 527 requested page) and ``totalCount`` (the total number of contexts in the 528 knowledge base, ignoring ``offset``/``limit``). 529 """ 530 params = { 531 key: str(value) 532 for key, value in {"offset": offset, "limit": limit, "search": search}.items() 533 if value is not None 534 } 535 result = await self._http.get( 536 f"squid-api/v1/ai/knowledge-base/listContextsPage/{self._kb_id}", 537 params=params or None, 538 ) 539 return result if result else {"contexts": [], "totalCount": 0} 540 541 async def upsert_contexts( 542 self, 543 contexts: list[ContextRequest], 544 files: list[tuple[str, bytes, str]] | None = None, 545 ) -> dict: 546 """Add or update contexts in the knowledge base. 547 548 Args: 549 contexts: A list of context request objects. Each must be either: 550 - A :class:`TextContextRequest`: ``{'contextId', 'type': 'text', 'title', 'text', ...}`` 551 - A :class:`FileContextRequest`: ``{'contextId', 'type': 'file', ...}`` 552 files: For file contexts, provide the actual file data as a list of 553 ``(filename, data_bytes, content_type)`` tuples. Must match the 554 order of file contexts in the ``contexts`` list. 555 556 Returns: 557 A dict with ``failures``: a list of ``UpsertContextStatusError`` dicts 558 for any contexts that failed to upsert. 559 560 Example:: 561 562 await kb.upsert_contexts( 563 [ 564 {"contextId": "doc-1", "type": "text", "title": "FAQ", "text": "..."}, 565 {"contextId": "doc-2", "type": "file"}, 566 ], 567 files=[ 568 ("manual.pdf", pdf_bytes, "application/pdf"), 569 ], 570 ) 571 """ 572 form_data = { 573 "knowledgeBaseId": self._kb_id, 574 "contexts": json.dumps(contexts), 575 } 576 file_tuples: list[tuple[str, tuple[str, bytes, str]]] = [] 577 if files: 578 for fname, fdata, ftype in files: 579 file_tuples.append(("files", (fname, fdata, ftype))) 580 return await self._http.post_form( 581 "squid-api/v1/ai/knowledge-base/upsertContexts", 582 data=form_data, 583 files=file_tuples, 584 ) 585 586 async def delete_contexts(self, context_ids: list[str]) -> None: 587 """Delete contexts by their IDs. 588 589 Args: 590 context_ids: List of context IDs to delete. 591 """ 592 await self._http.post( 593 "squid-api/v1/ai/knowledge-base/deleteContexts", 594 {"knowledgeBaseId": self._kb_id, "contextIds": context_ids}, 595 ) 596 597 # --- Search --- 598 599 async def search( 600 self, 601 prompt: str, 602 options: KnowledgeBaseSearchOptions | None = None, 603 ) -> list[dict]: 604 """Search the knowledge base using semantic search. 605 606 Args: 607 prompt: The search query in natural language. 608 options: Search options. See :class:`KnowledgeBaseSearchOptions`. 609 Supports: ``limit``, ``chunkLimit``, ``rerankProvider``, ``chatModel``. 610 611 Returns: 612 A list of ``AiKnowledgeBaseSearchResultChunk`` dicts, each with: 613 ``contextId``, ``data``, ``metadata``, ``score``. 614 615 Example:: 616 617 chunks = await kb.search( 618 "How do I reset my password?", 619 options={ 620 "limit": 5, 621 "chatModel": "gemini-3-flash", 622 }, 623 ) 624 for chunk in chunks: 625 print(f"Score: {chunk['score']}, Data: {chunk['data'][:100]}") 626 """ 627 search_options: dict[str, Any] = {"prompt": prompt, **(options or {})} 628 result = await self._http.post( 629 "squid-api/v1/ai/knowledge-base/search", 630 { 631 "knowledgeBaseId": self._kb_id, 632 "prompt": prompt, 633 "options": search_options, 634 }, 635 ) 636 return result.get("chunks", []) if result else []
Operations on a single knowledge base.
Provides methods for managing knowledge base configuration, upserting and searching text/file contexts, and retrieving individual contexts.
Obtained via AiClient.knowledge_base().
Example::
kb = squid.ai().knowledge_base("my-kb")
await kb.upsert(description="Product documentation")
await kb.upsert_contexts(
[
{
"contextId": "doc-1",
"type": "text",
"title": "Getting Started",
"text": "Welcome to our product...",
}
]
)
results = await kb.search("How do I get started?")
434 async def get(self) -> dict | None: 435 """Get the knowledge base details. 436 437 Returns: 438 An ``AiKnowledgeBase`` dict with keys: ``id``, ``appId``, 439 ``description``, ``metadataFields``, ``embeddingModel``, 440 ``chatModel``, ``updatedAt``. Returns ``None`` if not found. 441 """ 442 return await self._http.get(f"squid-api/v1/ai/knowledge-base/get/{self._kb_id}")
Get the knowledge base details.
Returns:
An
AiKnowledgeBasedict with keys:id,appId,description,metadataFields,embeddingModel,chatModel,updatedAt. ReturnsNoneif not found.
444 async def upsert( 445 self, 446 *, 447 description: str | None = None, 448 metadata_fields: list[AiKnowledgeBaseMetadataField] | None = None, 449 embedding_model: str | None = None, 450 chat_model: AiChatModelSelection | None = None, 451 name: str | None = None, 452 ) -> None: 453 """Create or update the knowledge base. 454 455 Args: 456 description: Description of the knowledge base's content. 457 metadata_fields: Schema for metadata fields used in filtering. 458 Each field: ``{'name': str, 'dataType': str, 'required': bool, 'description'?: str}``. 459 embedding_model: The embedding model name for vectorization. 460 chat_model: The LLM model for answering questions over this KB. 461 name: Display name for the knowledge base. 462 """ 463 kb: dict[str, Any] = {"id": self._kb_id} 464 if description is not None: 465 kb["description"] = description 466 if metadata_fields is not None: 467 kb["metadataFields"] = metadata_fields 468 if embedding_model is not None: 469 kb["embeddingModel"] = embedding_model 470 if chat_model is not None: 471 kb["chatModel"] = chat_model 472 if name is not None: 473 kb["name"] = name 474 await self._http.post("squid-api/v1/ai/knowledge-base/upsert", {"knowledgeBase": kb})
Create or update the knowledge base.
Arguments:
- description: Description of the knowledge base's content.
- metadata_fields: Schema for metadata fields used in filtering.
Each field:
{'name': str, 'dataType': str, 'required': bool, 'description'?: str}. - embedding_model: The embedding model name for vectorization.
- chat_model: The LLM model for answering questions over this KB.
- name: Display name for the knowledge base.
476 async def delete(self) -> None: 477 """Delete the knowledge base and all its contexts permanently.""" 478 await self._http.post("squid-api/v1/ai/knowledge-base/delete", {"id": self._kb_id})
Delete the knowledge base and all its contexts permanently.
482 async def get_context(self, context_id: str) -> dict | None: 483 """Get a specific context entry. 484 485 Args: 486 context_id: The unique context identifier. 487 488 Returns: 489 An ``AiKnowledgeBaseContext`` dict with keys: ``id``, ``appId``, 490 ``knowledgeBaseId``, ``createdAt``, ``updatedAt``, ``type``, 491 ``title``, ``text``, ``preview``, ``sizeBytes``, ``metadata``, 492 ``requestConfig``. Returns ``None`` if not found. 493 """ 494 return await self._http.get( 495 f"squid-api/v1/ai/knowledge-base/getContext/{self._kb_id}/{context_id}" 496 )
Get a specific context entry.
Arguments:
- context_id: The unique context identifier.
Returns:
An
AiKnowledgeBaseContextdict with keys:id,appId,knowledgeBaseId,createdAt,updatedAt,type,title,text,preview,sizeBytes,metadata,requestConfig. ReturnsNoneif not found.
498 async def list_contexts(self) -> list[dict]: 499 """List all contexts in the knowledge base. 500 501 Deprecated: fetches every context in one call with no pagination — expensive for large 502 knowledge bases. Use :meth:`list_contexts_page` instead, which supports 503 ``offset``/``limit``/``search``. 504 505 Returns: 506 A list of ``AiKnowledgeBaseContext`` dicts. 507 """ 508 result = await self._http.get(f"squid-api/v1/ai/knowledge-base/listContexts/{self._kb_id}") 509 return result.get("contexts", []) if result else []
List all contexts in the knowledge base.
Deprecated: fetches every context in one call with no pagination — expensive for large
knowledge bases. Use list_contexts_page() instead, which supports
offset/limit/search.
Returns:
A list of
AiKnowledgeBaseContextdicts.
511 async def list_contexts_page( 512 self, 513 *, 514 offset: int | None = None, 515 limit: int | None = None, 516 search: str | None = None, 517 ) -> dict: 518 """List a page of contexts in the knowledge base. 519 520 Args: 521 offset: The number of contexts to skip, for pagination. 522 limit: The maximum number of contexts to return, for pagination. 523 search: Case-insensitive substring search across id/title only. 524 525 Returns: 526 A dict with ``contexts`` (a list of ``AiKnowledgeBaseContext`` dicts for the 527 requested page) and ``totalCount`` (the total number of contexts in the 528 knowledge base, ignoring ``offset``/``limit``). 529 """ 530 params = { 531 key: str(value) 532 for key, value in {"offset": offset, "limit": limit, "search": search}.items() 533 if value is not None 534 } 535 result = await self._http.get( 536 f"squid-api/v1/ai/knowledge-base/listContextsPage/{self._kb_id}", 537 params=params or None, 538 ) 539 return result if result else {"contexts": [], "totalCount": 0}
List a page of contexts in the knowledge base.
Arguments:
- offset: The number of contexts to skip, for pagination.
- limit: The maximum number of contexts to return, for pagination.
- search: Case-insensitive substring search across id/title only.
Returns:
A dict with
contexts(a list ofAiKnowledgeBaseContextdicts for the requested page) andtotalCount(the total number of contexts in the knowledge base, ignoringoffset/limit).
541 async def upsert_contexts( 542 self, 543 contexts: list[ContextRequest], 544 files: list[tuple[str, bytes, str]] | None = None, 545 ) -> dict: 546 """Add or update contexts in the knowledge base. 547 548 Args: 549 contexts: A list of context request objects. Each must be either: 550 - A :class:`TextContextRequest`: ``{'contextId', 'type': 'text', 'title', 'text', ...}`` 551 - A :class:`FileContextRequest`: ``{'contextId', 'type': 'file', ...}`` 552 files: For file contexts, provide the actual file data as a list of 553 ``(filename, data_bytes, content_type)`` tuples. Must match the 554 order of file contexts in the ``contexts`` list. 555 556 Returns: 557 A dict with ``failures``: a list of ``UpsertContextStatusError`` dicts 558 for any contexts that failed to upsert. 559 560 Example:: 561 562 await kb.upsert_contexts( 563 [ 564 {"contextId": "doc-1", "type": "text", "title": "FAQ", "text": "..."}, 565 {"contextId": "doc-2", "type": "file"}, 566 ], 567 files=[ 568 ("manual.pdf", pdf_bytes, "application/pdf"), 569 ], 570 ) 571 """ 572 form_data = { 573 "knowledgeBaseId": self._kb_id, 574 "contexts": json.dumps(contexts), 575 } 576 file_tuples: list[tuple[str, tuple[str, bytes, str]]] = [] 577 if files: 578 for fname, fdata, ftype in files: 579 file_tuples.append(("files", (fname, fdata, ftype))) 580 return await self._http.post_form( 581 "squid-api/v1/ai/knowledge-base/upsertContexts", 582 data=form_data, 583 files=file_tuples, 584 )
Add or update contexts in the knowledge base.
Arguments:
- contexts: A list of context request objects. Each must be either:
- A
TextContextRequest:{'contextId', 'type': 'text', 'title', 'text', ...} - A
FileContextRequest:{'contextId', 'type': 'file', ...}
- A
- files: For file contexts, provide the actual file data as a list of
(filename, data_bytes, content_type)tuples. Must match the order of file contexts in thecontextslist.
Returns:
A dict with
failures: a list ofUpsertContextStatusErrordicts for any contexts that failed to upsert.
Example::
await kb.upsert_contexts(
[
{"contextId": "doc-1", "type": "text", "title": "FAQ", "text": "..."},
{"contextId": "doc-2", "type": "file"},
],
files=[
("manual.pdf", pdf_bytes, "application/pdf"),
],
)
586 async def delete_contexts(self, context_ids: list[str]) -> None: 587 """Delete contexts by their IDs. 588 589 Args: 590 context_ids: List of context IDs to delete. 591 """ 592 await self._http.post( 593 "squid-api/v1/ai/knowledge-base/deleteContexts", 594 {"knowledgeBaseId": self._kb_id, "contextIds": context_ids}, 595 )
Delete contexts by their IDs.
Arguments:
- context_ids: List of context IDs to delete.
599 async def search( 600 self, 601 prompt: str, 602 options: KnowledgeBaseSearchOptions | None = None, 603 ) -> list[dict]: 604 """Search the knowledge base using semantic search. 605 606 Args: 607 prompt: The search query in natural language. 608 options: Search options. See :class:`KnowledgeBaseSearchOptions`. 609 Supports: ``limit``, ``chunkLimit``, ``rerankProvider``, ``chatModel``. 610 611 Returns: 612 A list of ``AiKnowledgeBaseSearchResultChunk`` dicts, each with: 613 ``contextId``, ``data``, ``metadata``, ``score``. 614 615 Example:: 616 617 chunks = await kb.search( 618 "How do I reset my password?", 619 options={ 620 "limit": 5, 621 "chatModel": "gemini-3-flash", 622 }, 623 ) 624 for chunk in chunks: 625 print(f"Score: {chunk['score']}, Data: {chunk['data'][:100]}") 626 """ 627 search_options: dict[str, Any] = {"prompt": prompt, **(options or {})} 628 result = await self._http.post( 629 "squid-api/v1/ai/knowledge-base/search", 630 { 631 "knowledgeBaseId": self._kb_id, 632 "prompt": prompt, 633 "options": search_options, 634 }, 635 ) 636 return result.get("chunks", []) if result else []
Search the knowledge base using semantic search.
Arguments:
- prompt: The search query in natural language.
- options: Search options. See
KnowledgeBaseSearchOptions. Supports:limit,chunkLimit,rerankProvider,chatModel.
Returns:
A list of
AiKnowledgeBaseSearchResultChunkdicts, each with:contextId,data,metadata,score.
Example::
chunks = await kb.search(
"How do I reset my password?",
options={
"limit": 5,
"chatModel": "gemini-3-flash",
},
)
for chunk in chunks:
print(f"Score: {chunk['score']}, Data: {chunk['data'][:100]}")
474class KnowledgeBaseSearchOptions(TypedDict, total=False): 475 """Options for knowledge base search.""" 476 477 prompt: str 478 """The search prompt.""" 479 limit: int 480 """Max number of results to return.""" 481 chunkLimit: int 482 """How many chunks to search over (default 100).""" 483 rerankProvider: AiRerankProvider 484 """Reranker provider (default 'cohere').""" 485 chatModel: AiChatModelSelection 486 """Model to use for answering.""" 487 searchMode: Literal["vector", "hybrid", "keyword"] 488 """Retrieval mode: 'hybrid' (default; BM25+dense fusion where supported), 'vector' (dense only), or 489 'keyword' (pure lexical — every whitespace-separated term must appear as a literal, case-insensitive 490 substring)."""
Options for knowledge base search.
21class MatchmakingClient: 22 """AI-powered matchmaking: match makers, entities, matching.""" 23 24 def __init__(self, http: HttpTransport) -> None: 25 self._http = http 26 27 # --- Match makers --- 28 29 async def create_match_maker( 30 self, 31 match_maker_id: str, 32 description: str, 33 categories: list[MmCategory], 34 ) -> dict: 35 """Create a new match maker.""" 36 return await self._http.post( 37 "squid-api/v1/ai/matchmaking/createMatchMaker", 38 {"id": match_maker_id, "description": description, "categories": categories}, 39 ) 40 41 async def get_match_maker(self, match_maker_id: str) -> dict | None: 42 """Get a match maker by ID.""" 43 result = await self._http.get(f"squid-api/v1/ai/matchmaking/getMatchMaker/{match_maker_id}") 44 return result.get("matchMaker") if result else None 45 46 async def list_match_makers(self) -> list[dict]: 47 """List all match makers.""" 48 result = await self._http.get("squid-api/v1/ai/matchmaking/listMatchMakers") 49 return result.get("matchMakers", []) if result else [] 50 51 async def delete_match_maker(self, match_maker_id: str) -> None: 52 """Delete a match maker.""" 53 await self._http.post( 54 "squid-api/v1/ai/matchmaking/deleteMatchMaker", 55 {"matchMakerId": match_maker_id}, 56 ) 57 58 # --- Entities --- 59 60 async def insert_entities(self, match_maker_id: str, entities: list[MmEntity]) -> None: 61 """Insert entities into a match maker.""" 62 await self._http.post( 63 "squid-api/v1/ai/matchmaking/insertEntities", 64 {"matchMakerId": match_maker_id, "entities": entities}, 65 ) 66 67 async def delete_entity(self, match_maker_id: str, entity_id: str) -> None: 68 """Delete an entity.""" 69 await self._http.post( 70 "squid-api/v1/ai/matchmaking/deleteEntity", 71 {"matchMakerId": match_maker_id, "entityId": entity_id}, 72 ) 73 74 async def get_entity(self, match_maker_id: str, entity_id: str) -> dict | None: 75 """Get a specific entity.""" 76 result = await self._http.get( 77 f"squid-api/v1/ai/matchmaking/getEntity/{match_maker_id}/{entity_id}" 78 ) 79 return result.get("entity") if result else None 80 81 async def list_entities( 82 self, 83 match_maker_id: str, 84 category_id: str, 85 options: MmListEntitiesOptions | None = None, 86 ) -> list[dict]: 87 """List entities in a category.""" 88 result = await self._http.post( 89 "squid-api/v1/ai/matchmaking/listEntities", 90 { 91 "matchMakerId": match_maker_id, 92 "categoryId": category_id, 93 "options": options or {}, 94 }, 95 ) 96 return result.get("entities", []) if result else [] 97 98 # --- Matching --- 99 100 async def find_matches( 101 self, 102 match_maker_id: str, 103 entity_id: str, 104 options: MmFindMatchesOptions | None = None, 105 ) -> list[dict]: 106 """Find matches for an existing entity. 107 108 Returns list of MmEntityMatch dicts with: 109 id, content, categoryId, metadata, score, reasoning. 110 """ 111 result = await self._http.post( 112 "squid-api/v1/ai/matchmaking/findMatches", 113 { 114 "matchMakerId": match_maker_id, 115 "entityId": entity_id, 116 "options": options or {}, 117 }, 118 ) 119 return result.get("matches", []) if result else [] 120 121 async def find_matches_for_entity( 122 self, 123 match_maker_id: str, 124 entity: MmEntity, 125 options: MmFindMatchesOptions | None = None, 126 ) -> list[dict]: 127 """Find matches for a new entity (not yet inserted).""" 128 result = await self._http.post( 129 "squid-api/v1/ai/matchmaking/findMatchesForEntity", 130 { 131 "matchMakerId": match_maker_id, 132 "entity": entity, 133 "options": options or {}, 134 }, 135 ) 136 return result.get("matches", []) if result else []
AI-powered matchmaking: match makers, entities, matching.
29 async def create_match_maker( 30 self, 31 match_maker_id: str, 32 description: str, 33 categories: list[MmCategory], 34 ) -> dict: 35 """Create a new match maker.""" 36 return await self._http.post( 37 "squid-api/v1/ai/matchmaking/createMatchMaker", 38 {"id": match_maker_id, "description": description, "categories": categories}, 39 )
Create a new match maker.
41 async def get_match_maker(self, match_maker_id: str) -> dict | None: 42 """Get a match maker by ID.""" 43 result = await self._http.get(f"squid-api/v1/ai/matchmaking/getMatchMaker/{match_maker_id}") 44 return result.get("matchMaker") if result else None
Get a match maker by ID.
46 async def list_match_makers(self) -> list[dict]: 47 """List all match makers.""" 48 result = await self._http.get("squid-api/v1/ai/matchmaking/listMatchMakers") 49 return result.get("matchMakers", []) if result else []
List all match makers.
51 async def delete_match_maker(self, match_maker_id: str) -> None: 52 """Delete a match maker.""" 53 await self._http.post( 54 "squid-api/v1/ai/matchmaking/deleteMatchMaker", 55 {"matchMakerId": match_maker_id}, 56 )
Delete a match maker.
60 async def insert_entities(self, match_maker_id: str, entities: list[MmEntity]) -> None: 61 """Insert entities into a match maker.""" 62 await self._http.post( 63 "squid-api/v1/ai/matchmaking/insertEntities", 64 {"matchMakerId": match_maker_id, "entities": entities}, 65 )
Insert entities into a match maker.
67 async def delete_entity(self, match_maker_id: str, entity_id: str) -> None: 68 """Delete an entity.""" 69 await self._http.post( 70 "squid-api/v1/ai/matchmaking/deleteEntity", 71 {"matchMakerId": match_maker_id, "entityId": entity_id}, 72 )
Delete an entity.
74 async def get_entity(self, match_maker_id: str, entity_id: str) -> dict | None: 75 """Get a specific entity.""" 76 result = await self._http.get( 77 f"squid-api/v1/ai/matchmaking/getEntity/{match_maker_id}/{entity_id}" 78 ) 79 return result.get("entity") if result else None
Get a specific entity.
81 async def list_entities( 82 self, 83 match_maker_id: str, 84 category_id: str, 85 options: MmListEntitiesOptions | None = None, 86 ) -> list[dict]: 87 """List entities in a category.""" 88 result = await self._http.post( 89 "squid-api/v1/ai/matchmaking/listEntities", 90 { 91 "matchMakerId": match_maker_id, 92 "categoryId": category_id, 93 "options": options or {}, 94 }, 95 ) 96 return result.get("entities", []) if result else []
List entities in a category.
100 async def find_matches( 101 self, 102 match_maker_id: str, 103 entity_id: str, 104 options: MmFindMatchesOptions | None = None, 105 ) -> list[dict]: 106 """Find matches for an existing entity. 107 108 Returns list of MmEntityMatch dicts with: 109 id, content, categoryId, metadata, score, reasoning. 110 """ 111 result = await self._http.post( 112 "squid-api/v1/ai/matchmaking/findMatches", 113 { 114 "matchMakerId": match_maker_id, 115 "entityId": entity_id, 116 "options": options or {}, 117 }, 118 ) 119 return result.get("matches", []) if result else []
Find matches for an existing entity.
Returns list of MmEntityMatch dicts with: id, content, categoryId, metadata, score, reasoning.
121 async def find_matches_for_entity( 122 self, 123 match_maker_id: str, 124 entity: MmEntity, 125 options: MmFindMatchesOptions | None = None, 126 ) -> list[dict]: 127 """Find matches for a new entity (not yet inserted).""" 128 result = await self._http.post( 129 "squid-api/v1/ai/matchmaking/findMatchesForEntity", 130 { 131 "matchMakerId": match_maker_id, 132 "entity": entity, 133 "options": options or {}, 134 }, 135 ) 136 return result.get("matches", []) if result else []
Find matches for a new entity (not yet inserted).
596class MmCategory(TypedDict): 597 """Matchmaking category.""" 598 599 id: str 600 description: str
Matchmaking category.
603class MmEntity(TypedDict, total=False): 604 """Matchmaking entity.""" 605 606 id: str 607 content: str 608 categoryId: str 609 metadata: dict[str, Any]
Matchmaking entity.
612class MmFindMatchesOptions(TypedDict, total=False): 613 """Options for finding matches.""" 614 615 metadataFilter: dict[str, Any] 616 """AiContextMetadataFilter conditions.""" 617 limit: int 618 """Max matches to return (default 100, max 100).""" 619 matchToCategoryId: str 620 """Category to match against."""
Options for finding matches.
623class MmListEntitiesOptions(TypedDict, total=False): 624 """Options for listing entities.""" 625 626 metadataFilter: dict[str, Any] 627 limit: int
Options for listing entities.
44class ModelIdSpec(TypedDict, total=False): 45 """An AI chat model available to the app. 46 47 Returned by :meth:`AiClient.list_chat_models`. 48 """ 49 50 modelId: AiChatModelName 51 """The model ID used for API calls. Required.""" 52 integrationId: str 53 """The integration ID if this model comes from an integration (OpenAI-compatible, 54 Bedrock). Absent for Squid-provided models.""" 55 displayName: str 56 """Human-readable display name for the model (e.g. 'GPT-4o').""" 57 description: str 58 """Short human-readable description of the model. Absent for custom integration models.""" 59 replacedBy: AiChatModelName 60 """Set only for deprecated models: the active model that calls to this model are 61 routed to. Absent for active models.""" 62 source: AiModelSource 63 """Where the model comes from: 'vendor' (Squid-provided), 'connector' (provided by an 64 integration configured on the app), or 'custom' (user-added model from the app's bundle)."""
An AI chat model available to the app.
Returned by AiClient.list_chat_models().
The integration ID if this model comes from an integration (OpenAI-compatible, Bedrock). Absent for Squid-provided models.
Short human-readable description of the model. Absent for custom integration models.
24class Squid: 25 """Squid Cloud Python client. 26 27 The main entry point for interacting with the Squid Cloud platform. 28 Provides access to AI agents, knowledge bases, web utilities, 29 matchmaking, document extraction, backend functions, and webhooks. 30 31 Usage:: 32 33 squid = Squid( 34 app_id="my-app", 35 api_key="sk-...", 36 region="us-east-1.aws", 37 environment_id="dev", 38 ) 39 40 # AI agent 41 response = await squid.ai().agent("my-agent").ask("Hello!") 42 43 # Execute backend function 44 result = await squid.execute_function("MyService:greet", "World") 45 46 # Web search 47 results = await squid.web().ai_search("latest news") 48 49 # Cleanup 50 await squid.close() 51 52 Can also be used as an async context manager:: 53 54 async with Squid(app_id="my-app", api_key="sk-...", region="us-east-1.aws") as squid: 55 result = await squid.ai().agent("my-agent").ask("Hello!") 56 """ 57 58 def __init__( 59 self, 60 app_id: str, 61 region: str, 62 api_key: str | None = None, 63 environment_id: str | None = None, 64 squid_developer_id: str | None = None, 65 ) -> None: 66 """Initialize the Squid client. 67 68 Args: 69 app_id: The Squid application ID. 70 region: The deployment region (e.g., 'us-east-1.aws', 'local'). 71 api_key: API key for authentication. Required for most operations. 72 environment_id: Environment identifier (e.g., 'dev', 'prod'). 73 Appended to app_id as '{app_id}-{environment_id}'. 74 squid_developer_id: Developer identifier for local development. 75 Appended to app_id as '{app_id}-{environment_id}-{developer_id}'. 76 """ 77 self._app_id = app_id 78 self._region = region 79 self._environment_id = environment_id 80 self._squid_developer_id = squid_developer_id 81 82 full_app_id = app_id 83 if environment_id: 84 full_app_id = f"{app_id}-{environment_id}" 85 if squid_developer_id: 86 full_app_id = f"{full_app_id}-{squid_developer_id}" 87 88 self._full_app_id = full_app_id 89 self._http = HttpTransport( 90 app_id=full_app_id, 91 region=region, 92 api_key=api_key, 93 ) 94 95 @property 96 def app_id(self) -> str: 97 """The application ID (without environment/developer suffix).""" 98 return self._app_id 99 100 @property 101 def region(self) -> str: 102 """The deployment region.""" 103 return self._region 104 105 @property 106 def client_id(self) -> str: 107 """The unique client instance ID (UUID generated per Squid instance).""" 108 return self._http.client_id 109 110 # --- Sub-clients --- 111 112 def ai(self) -> AiClient: 113 """Access AI operations. 114 115 Provides access to AI agents, knowledge bases, image generation, 116 and audio transcription/synthesis. 117 118 Returns: 119 An :class:`AiClient` instance. 120 121 Example:: 122 123 agent = squid.ai().agent("my-agent") 124 response = await agent.ask("What is the weather?") 125 126 kb = squid.ai().knowledge_base("my-kb") 127 results = await kb.search("query") 128 """ 129 return AiClient(self._http) 130 131 def web(self) -> WebClient: 132 """Access web utilities. 133 134 Provides AI-powered web search, URL content extraction, 135 and short URL management. 136 137 Returns: 138 A :class:`WebClient` instance. 139 140 Example:: 141 142 content = await squid.web().get_url_content("https://example.com") 143 results = await squid.web().ai_search("latest AI news") 144 """ 145 return WebClient(self._http) 146 147 def matchmaking(self) -> MatchmakingClient: 148 """Access AI-powered matchmaking. 149 150 Provides match maker management, entity CRUD, 151 and AI-powered entity matching. 152 153 Returns: 154 A :class:`MatchmakingClient` instance. 155 156 Example:: 157 158 mm = squid.matchmaking() 159 await mm.create_match_maker("jobs", "Job matching", categories=[...]) 160 matches = await mm.find_matches("jobs", "entity-1") 161 """ 162 return MatchmakingClient(self._http) 163 164 def extraction(self) -> ExtractionClient: 165 """Access document extraction and PDF creation. 166 167 Provides PDF generation from HTML or URLs, and structured data 168 extraction from documents (PDF, DOCX, images, etc.). 169 170 Returns: 171 An :class:`ExtractionClient` instance. 172 173 Example:: 174 175 pdf = await squid.extraction().create_pdf_from_html("<h1>Hello</h1>") 176 data = await squid.extraction().extract_data_from_document_url( 177 "https://example.com/doc.pdf" 178 ) 179 """ 180 return ExtractionClient(self._http) 181 182 # --- Execute backend function --- 183 184 async def execute_function( 185 self, 186 function_name: str, 187 *params: Any, 188 ) -> Any: 189 """Execute a backend function by name. 190 191 Calls a function defined in a Squid backend service using the 192 ``@executable()`` decorator. 193 194 Args: 195 function_name: The service function name in the format 196 ``"ClassName:methodName"`` (e.g., ``"MyService:greet"``). 197 *params: Positional arguments to pass to the function. 198 Must be JSON-serializable. 199 200 Returns: 201 The function's return value, deserialized from JSON. 202 203 Raises: 204 SquidHttpError: If the function is not found or throws an error. 205 206 Example:: 207 208 result = await squid.execute_function("MyService:greet", "World") 209 # result == "Hello, World!" 210 211 data = await squid.execute_function("MyService:getData", 42, True) 212 """ 213 result = await self._http.post( 214 f"backend-function/execute?{function_name}", 215 { 216 "functionName": function_name, 217 "paramsArrayStr": json.dumps(list(params)), 218 }, 219 ) 220 if isinstance(result, dict): 221 payload = result.get("payload") 222 if isinstance(payload, str): 223 return json.loads(payload) 224 return payload 225 return result 226 227 # --- Execute webhook --- 228 229 async def execute_webhook( 230 self, 231 webhook_id: str, 232 *, 233 body: Any = None, 234 headers: dict[str, str] | None = None, 235 method: str = "POST", 236 ) -> Any: 237 """Execute a webhook. 238 239 Calls a webhook endpoint defined in a Squid backend service 240 using the ``@webhook()`` decorator. 241 242 Args: 243 webhook_id: The webhook ID as defined in the ``@webhook("id")`` decorator. 244 body: The request body to send. Must be JSON-serializable. 245 headers: Extra HTTP headers to include in the request. 246 method: The HTTP method to use (default ``"POST"``). 247 248 Returns: 249 The webhook's response body, deserialized from JSON. 250 251 Raises: 252 SquidHttpError: If the webhook is not found or returns an error. 253 254 Example:: 255 256 result = await squid.execute_webhook("my-hook", body={"key": "value"}) 257 """ 258 return await self._http.post( 259 f"webhooks/{webhook_id}", 260 body, 261 extra_headers=headers, 262 ) 263 264 def get_webhook_url(self, webhook_id: str) -> str: 265 """Get the full URL for a webhook endpoint. 266 267 Useful for providing the webhook URL to external services that 268 need to send HTTP requests to your Squid backend. 269 270 Args: 271 webhook_id: The webhook ID. 272 273 Returns: 274 The full URL string (e.g., 275 ``"https://myapp.us-east-1.aws.squid.cloud/webhooks/my-hook"``). 276 277 Example:: 278 279 url = squid.get_webhook_url("stripe-events") 280 # url == "https://myapp-dev.us-east-1.aws.squid.cloud/webhooks/stripe-events" 281 """ 282 return build_url(self._region, self._full_app_id, f"webhooks/{webhook_id}") 283 284 # --- AI Query --- 285 286 async def execute_ai_query( 287 self, 288 integration_id: str, 289 prompt: str, 290 *, 291 options: AiQueryOptions | None = None, 292 response_format: dict[str, Any] | None = None, 293 ) -> dict: 294 """Execute an AI-powered database query. 295 296 Uses AI to generate and execute database queries based on a 297 natural language prompt. 298 299 Args: 300 integration_id: The database integration ID to query against. 301 prompt: A natural language description of the data you want. 302 options: Optional :class:`AiQueryOptions` controlling collection 303 selection, query generation (including ``allowClarification``), 304 result analysis (including ``enableCodeInterpreter``), memory, 305 AI validation, per-stage model overrides via ``aiOptions``, 306 and custom instructions. 307 response_format: Optional structured output format, e.g., 308 ``{"type": "json_schema", "schema": {...}}``. 309 310 Returns: 311 An ``AiQueryResponse`` dict containing: 312 - ``answer`` (str): The AI-generated answer. 313 - ``explanation`` (str): How the answer was derived. 314 - ``executedQueries`` (list): The actual queries that were run. 315 - ``success`` (bool): Whether the query succeeded. 316 - ``usedCodeInterpreter`` (bool): Whether the code 317 interpreter was used to analyze results. 318 - ``clarificationQuestion`` (str): If the AI needs more info. 319 320 Example:: 321 322 result = await squid.execute_ai_query( 323 "my-database", 324 "How many users signed up last week?", 325 options={ 326 "selectCollectionsOptions": {"collectionsToUse": ["users"]}, 327 "analyzeResultsOptions": {"enableCodeInterpreter": True}, 328 }, 329 ) 330 print(result["answer"]) 331 """ 332 return await execute_ai_query( 333 self._http, 334 integration_id, 335 prompt, 336 options=options, 337 response_format=response_format, 338 ) 339 340 # --- Lifecycle --- 341 342 async def close(self) -> None: 343 """Close the HTTP client and release resources. 344 345 Should be called when the Squid client is no longer needed. 346 Alternatively, use the client as an async context manager. 347 """ 348 await self._http.close() 349 350 async def __aenter__(self) -> Squid: 351 """Enter async context manager.""" 352 return self 353 354 async def __aexit__(self, *args: Any) -> None: 355 """Exit async context manager and close resources.""" 356 await self.close()
Squid Cloud Python client.
The main entry point for interacting with the Squid Cloud platform. Provides access to AI agents, knowledge bases, web utilities, matchmaking, document extraction, backend functions, and webhooks.
Usage::
squid = Squid(
app_id="my-app",
api_key="sk-...",
region="us-east-1.aws",
environment_id="dev",
)
# AI agent
response = await squid.ai().agent("my-agent").ask("Hello!")
# Execute backend function
result = await squid.execute_function("MyService:greet", "World")
# Web search
results = await squid.web().ai_search("latest news")
# Cleanup
await squid.close()
Can also be used as an async context manager::
async with Squid(app_id="my-app", api_key="sk-...", region="us-east-1.aws") as squid:
result = await squid.ai().agent("my-agent").ask("Hello!")
58 def __init__( 59 self, 60 app_id: str, 61 region: str, 62 api_key: str | None = None, 63 environment_id: str | None = None, 64 squid_developer_id: str | None = None, 65 ) -> None: 66 """Initialize the Squid client. 67 68 Args: 69 app_id: The Squid application ID. 70 region: The deployment region (e.g., 'us-east-1.aws', 'local'). 71 api_key: API key for authentication. Required for most operations. 72 environment_id: Environment identifier (e.g., 'dev', 'prod'). 73 Appended to app_id as '{app_id}-{environment_id}'. 74 squid_developer_id: Developer identifier for local development. 75 Appended to app_id as '{app_id}-{environment_id}-{developer_id}'. 76 """ 77 self._app_id = app_id 78 self._region = region 79 self._environment_id = environment_id 80 self._squid_developer_id = squid_developer_id 81 82 full_app_id = app_id 83 if environment_id: 84 full_app_id = f"{app_id}-{environment_id}" 85 if squid_developer_id: 86 full_app_id = f"{full_app_id}-{squid_developer_id}" 87 88 self._full_app_id = full_app_id 89 self._http = HttpTransport( 90 app_id=full_app_id, 91 region=region, 92 api_key=api_key, 93 )
Initialize the Squid client.
Arguments:
- app_id: The Squid application ID.
- region: The deployment region (e.g., 'us-east-1.aws', 'local').
- api_key: API key for authentication. Required for most operations.
- environment_id: Environment identifier (e.g., 'dev', 'prod'). Appended to app_id as '{app_id}-{environment_id}'.
- squid_developer_id: Developer identifier for local development. Appended to app_id as '{app_id}-{environment_id}-{developer_id}'.
95 @property 96 def app_id(self) -> str: 97 """The application ID (without environment/developer suffix).""" 98 return self._app_id
The application ID (without environment/developer suffix).
105 @property 106 def client_id(self) -> str: 107 """The unique client instance ID (UUID generated per Squid instance).""" 108 return self._http.client_id
The unique client instance ID (UUID generated per Squid instance).
112 def ai(self) -> AiClient: 113 """Access AI operations. 114 115 Provides access to AI agents, knowledge bases, image generation, 116 and audio transcription/synthesis. 117 118 Returns: 119 An :class:`AiClient` instance. 120 121 Example:: 122 123 agent = squid.ai().agent("my-agent") 124 response = await agent.ask("What is the weather?") 125 126 kb = squid.ai().knowledge_base("my-kb") 127 results = await kb.search("query") 128 """ 129 return AiClient(self._http)
Access AI operations.
Provides access to AI agents, knowledge bases, image generation, and audio transcription/synthesis.
Returns:
An
AiClientinstance.
Example::
agent = squid.ai().agent("my-agent")
response = await agent.ask("What is the weather?")
kb = squid.ai().knowledge_base("my-kb")
results = await kb.search("query")
131 def web(self) -> WebClient: 132 """Access web utilities. 133 134 Provides AI-powered web search, URL content extraction, 135 and short URL management. 136 137 Returns: 138 A :class:`WebClient` instance. 139 140 Example:: 141 142 content = await squid.web().get_url_content("https://example.com") 143 results = await squid.web().ai_search("latest AI news") 144 """ 145 return WebClient(self._http)
Access web utilities.
Provides AI-powered web search, URL content extraction, and short URL management.
Returns:
A
WebClientinstance.
Example::
content = await squid.web().get_url_content("https://example.com")
results = await squid.web().ai_search("latest AI news")
147 def matchmaking(self) -> MatchmakingClient: 148 """Access AI-powered matchmaking. 149 150 Provides match maker management, entity CRUD, 151 and AI-powered entity matching. 152 153 Returns: 154 A :class:`MatchmakingClient` instance. 155 156 Example:: 157 158 mm = squid.matchmaking() 159 await mm.create_match_maker("jobs", "Job matching", categories=[...]) 160 matches = await mm.find_matches("jobs", "entity-1") 161 """ 162 return MatchmakingClient(self._http)
Access AI-powered matchmaking.
Provides match maker management, entity CRUD, and AI-powered entity matching.
Returns:
A
MatchmakingClientinstance.
Example::
mm = squid.matchmaking()
await mm.create_match_maker("jobs", "Job matching", categories=[...])
matches = await mm.find_matches("jobs", "entity-1")
164 def extraction(self) -> ExtractionClient: 165 """Access document extraction and PDF creation. 166 167 Provides PDF generation from HTML or URLs, and structured data 168 extraction from documents (PDF, DOCX, images, etc.). 169 170 Returns: 171 An :class:`ExtractionClient` instance. 172 173 Example:: 174 175 pdf = await squid.extraction().create_pdf_from_html("<h1>Hello</h1>") 176 data = await squid.extraction().extract_data_from_document_url( 177 "https://example.com/doc.pdf" 178 ) 179 """ 180 return ExtractionClient(self._http)
Access document extraction and PDF creation.
Provides PDF generation from HTML or URLs, and structured data extraction from documents (PDF, DOCX, images, etc.).
Returns:
An
ExtractionClientinstance.
Example::
pdf = await squid.extraction().create_pdf_from_html("<h1>Hello</h1>")
data = await squid.extraction().extract_data_from_document_url(
"https://example.com/doc.pdf"
)
184 async def execute_function( 185 self, 186 function_name: str, 187 *params: Any, 188 ) -> Any: 189 """Execute a backend function by name. 190 191 Calls a function defined in a Squid backend service using the 192 ``@executable()`` decorator. 193 194 Args: 195 function_name: The service function name in the format 196 ``"ClassName:methodName"`` (e.g., ``"MyService:greet"``). 197 *params: Positional arguments to pass to the function. 198 Must be JSON-serializable. 199 200 Returns: 201 The function's return value, deserialized from JSON. 202 203 Raises: 204 SquidHttpError: If the function is not found or throws an error. 205 206 Example:: 207 208 result = await squid.execute_function("MyService:greet", "World") 209 # result == "Hello, World!" 210 211 data = await squid.execute_function("MyService:getData", 42, True) 212 """ 213 result = await self._http.post( 214 f"backend-function/execute?{function_name}", 215 { 216 "functionName": function_name, 217 "paramsArrayStr": json.dumps(list(params)), 218 }, 219 ) 220 if isinstance(result, dict): 221 payload = result.get("payload") 222 if isinstance(payload, str): 223 return json.loads(payload) 224 return payload 225 return result
Execute a backend function by name.
Calls a function defined in a Squid backend service using the
@executable() decorator.
Arguments:
- function_name: The service function name in the format
"ClassName:methodName"(e.g.,"MyService:greet"). - *params: Positional arguments to pass to the function. Must be JSON-serializable.
Returns:
The function's return value, deserialized from JSON.
Raises:
- SquidHttpError: If the function is not found or throws an error.
Example::
result = await squid.execute_function("MyService:greet", "World")
# result == "Hello, World!"
data = await squid.execute_function("MyService:getData", 42, True)
229 async def execute_webhook( 230 self, 231 webhook_id: str, 232 *, 233 body: Any = None, 234 headers: dict[str, str] | None = None, 235 method: str = "POST", 236 ) -> Any: 237 """Execute a webhook. 238 239 Calls a webhook endpoint defined in a Squid backend service 240 using the ``@webhook()`` decorator. 241 242 Args: 243 webhook_id: The webhook ID as defined in the ``@webhook("id")`` decorator. 244 body: The request body to send. Must be JSON-serializable. 245 headers: Extra HTTP headers to include in the request. 246 method: The HTTP method to use (default ``"POST"``). 247 248 Returns: 249 The webhook's response body, deserialized from JSON. 250 251 Raises: 252 SquidHttpError: If the webhook is not found or returns an error. 253 254 Example:: 255 256 result = await squid.execute_webhook("my-hook", body={"key": "value"}) 257 """ 258 return await self._http.post( 259 f"webhooks/{webhook_id}", 260 body, 261 extra_headers=headers, 262 )
Execute a webhook.
Calls a webhook endpoint defined in a Squid backend service
using the @webhook() decorator.
Arguments:
- webhook_id: The webhook ID as defined in the
@webhook("id")decorator. - body: The request body to send. Must be JSON-serializable.
- headers: Extra HTTP headers to include in the request.
- method: The HTTP method to use (default
"POST").
Returns:
The webhook's response body, deserialized from JSON.
Raises:
- SquidHttpError: If the webhook is not found or returns an error.
Example::
result = await squid.execute_webhook("my-hook", body={"key": "value"})
264 def get_webhook_url(self, webhook_id: str) -> str: 265 """Get the full URL for a webhook endpoint. 266 267 Useful for providing the webhook URL to external services that 268 need to send HTTP requests to your Squid backend. 269 270 Args: 271 webhook_id: The webhook ID. 272 273 Returns: 274 The full URL string (e.g., 275 ``"https://myapp.us-east-1.aws.squid.cloud/webhooks/my-hook"``). 276 277 Example:: 278 279 url = squid.get_webhook_url("stripe-events") 280 # url == "https://myapp-dev.us-east-1.aws.squid.cloud/webhooks/stripe-events" 281 """ 282 return build_url(self._region, self._full_app_id, f"webhooks/{webhook_id}")
Get the full URL for a webhook endpoint.
Useful for providing the webhook URL to external services that need to send HTTP requests to your Squid backend.
Arguments:
- webhook_id: The webhook ID.
Returns:
The full URL string (e.g.,
"https://myapp.us-east-1.aws.squid.cloud/webhooks/my-hook").
Example::
url = squid.get_webhook_url("stripe-events")
# url == "https://myapp-dev.us-east-1.aws.squid.cloud/webhooks/stripe-events"
286 async def execute_ai_query( 287 self, 288 integration_id: str, 289 prompt: str, 290 *, 291 options: AiQueryOptions | None = None, 292 response_format: dict[str, Any] | None = None, 293 ) -> dict: 294 """Execute an AI-powered database query. 295 296 Uses AI to generate and execute database queries based on a 297 natural language prompt. 298 299 Args: 300 integration_id: The database integration ID to query against. 301 prompt: A natural language description of the data you want. 302 options: Optional :class:`AiQueryOptions` controlling collection 303 selection, query generation (including ``allowClarification``), 304 result analysis (including ``enableCodeInterpreter``), memory, 305 AI validation, per-stage model overrides via ``aiOptions``, 306 and custom instructions. 307 response_format: Optional structured output format, e.g., 308 ``{"type": "json_schema", "schema": {...}}``. 309 310 Returns: 311 An ``AiQueryResponse`` dict containing: 312 - ``answer`` (str): The AI-generated answer. 313 - ``explanation`` (str): How the answer was derived. 314 - ``executedQueries`` (list): The actual queries that were run. 315 - ``success`` (bool): Whether the query succeeded. 316 - ``usedCodeInterpreter`` (bool): Whether the code 317 interpreter was used to analyze results. 318 - ``clarificationQuestion`` (str): If the AI needs more info. 319 320 Example:: 321 322 result = await squid.execute_ai_query( 323 "my-database", 324 "How many users signed up last week?", 325 options={ 326 "selectCollectionsOptions": {"collectionsToUse": ["users"]}, 327 "analyzeResultsOptions": {"enableCodeInterpreter": True}, 328 }, 329 ) 330 print(result["answer"]) 331 """ 332 return await execute_ai_query( 333 self._http, 334 integration_id, 335 prompt, 336 options=options, 337 response_format=response_format, 338 )
Execute an AI-powered database query.
Uses AI to generate and execute database queries based on a natural language prompt.
Arguments:
- integration_id: The database integration ID to query against.
- prompt: A natural language description of the data you want.
- options: Optional
AiQueryOptionscontrolling collection selection, query generation (includingallowClarification), result analysis (includingenableCodeInterpreter), memory, AI validation, per-stage model overrides viaaiOptions, and custom instructions. - response_format: Optional structured output format, e.g.,
{"type": "json_schema", "schema": {...}}.
Returns:
An
AiQueryResponsedict containing: -answer(str): The AI-generated answer. -explanation(str): How the answer was derived. -executedQueries(list): The actual queries that were run. -success(bool): Whether the query succeeded. -usedCodeInterpreter(bool): Whether the code interpreter was used to analyze results. -clarificationQuestion(str): If the AI needs more info.
Example::
result = await squid.execute_ai_query(
"my-database",
"How many users signed up last week?",
options={
"selectCollectionsOptions": {"collectionsToUse": ["users"]},
"analyzeResultsOptions": {"enableCodeInterpreter": True},
},
)
print(result["answer"])
342 async def close(self) -> None: 343 """Close the HTTP client and release resources. 344 345 Should be called when the Squid client is no longer needed. 346 Alternatively, use the client as an async context manager. 347 """ 348 await self._http.close()
Close the HTTP client and release resources.
Should be called when the Squid client is no longer needed. Alternatively, use the client as an async context manager.
89class SquidHttpError(Exception): 90 """Raised when the Squid API returns an HTTP error response (status >= 400). 91 92 Attributes: 93 status_code: The HTTP status code. 94 url: The URL that was requested. 95 body: The parsed response body, if available. 96 """ 97 98 def __init__(self, status_code: int, message: str, url: str, body: Any = None): 99 self.status_code = status_code 100 self.url = url 101 self.body = body 102 super().__init__(f"HTTP {status_code}: {message} (url={url})")
Raised when the Squid API returns an HTTP error response (status >= 400).
Attributes:
- status_code: The HTTP status code.
- url: The URL that was requested.
- body: The parsed response body, if available.
579class StableDiffusionOptions(TypedDict, total=False): 580 """Options for Stable Diffusion Core image generation.""" 581 582 modelName: Literal["stable-diffusion-core"] 583 aspectRatio: Literal["16:9", "1:1", "21:9", "2:3", "3:2", "4:5", "5:4", "9:16", "9:21"] 584 negativePrompt: str 585 seed: int 586 stylePreset: str 587 outputFormat: str
Options for Stable Diffusion Core image generation.
439class TextContextRequest(TypedDict, total=False): 440 """Request to upsert a text context.""" 441 442 contextId: str 443 type: Literal["text"] 444 title: str 445 text: str 446 metadata: dict[str, Any] 447 options: AiContextTextOptions
Request to upsert a text context.
339class UpsertAgentOptions(TypedDict, total=False): 340 """Options for creating/updating an agent.""" 341 342 description: str 343 """Description of the agent's purpose.""" 344 isPublic: bool 345 """Whether the agent is publicly accessible.""" 346 auditLog: bool 347 """Enable audit logging.""" 348 apiKey: str 349 """API key for this agent.""" 350 options: AiChatOptions 351 """Default chat options."""
Options for creating/updating an agent.
697class WebAiSearchResponse(TypedDict): 698 """Response from AI web search.""" 699 700 markdownText: str 701 citedUrls: list[dict[str, str]]
Response from AI web search.
16class WebClient: 17 """Web utilities: AI search, URL content, short URLs.""" 18 19 def __init__(self, http: HttpTransport) -> None: 20 self._http = http 21 22 async def ai_search( 23 self, query: str, allowed_domains: list[str] | None = None 24 ) -> WebAiSearchResponse: 25 """Perform an AI-powered web search. 26 27 When allowed_domains is provided, the search is restricted to those domains 28 (subdomains included) and every cited URL belongs to one of them. 29 30 Returns WebAiSearchResponse with 'markdownText' and 'citedUrls'. 31 """ 32 body: dict[str, object] = {"query": query} 33 if allowed_domains is not None: 34 body["allowedDomains"] = allowed_domains 35 return await self._http.post("squid-api/v1/web/aiSearch", body) 36 37 async def get_url_content(self, url: str) -> str: 38 """Fetch and extract content from a URL as markdown.""" 39 result = await self._http.post("squid-api/v1/web/getUrlContent", {"url": url}) 40 if isinstance(result, dict): 41 return result.get("markdownText", "") 42 return str(result) if result else "" 43 44 async def create_short_url( 45 self, 46 url: str, 47 *, 48 seconds_to_live: int | None = None, 49 file_extension: str | None = None, 50 ) -> WebShortUrlResponse: 51 """Create a short URL. 52 53 Returns WebShortUrlResponse with 'id', 'shortUrl', 'expiry'. 54 """ 55 body: dict = {"url": url} 56 if seconds_to_live is not None: 57 body["secondsToLive"] = seconds_to_live 58 if file_extension is not None: 59 body["fileExtension"] = file_extension 60 return await self._http.post("squid-api/v1/web/createShortUrl", body) 61 62 async def create_short_urls( 63 self, 64 urls: list[str], 65 *, 66 seconds_to_live: int | None = None, 67 file_extension: str | None = None, 68 ) -> WebShortUrlBulkResponse: 69 """Create multiple short URLs in bulk. 70 71 Returns WebShortUrlBulkResponse with 'ids', 'shortUrls', 'expiry'. 72 """ 73 body: dict = {"urls": urls} 74 if seconds_to_live is not None: 75 body["secondsToLive"] = seconds_to_live 76 if file_extension is not None: 77 body["fileExtension"] = file_extension 78 return await self._http.post("squid-api/v1/web/createShortUrls", body) 79 80 async def delete_short_url(self, url_id: str) -> None: 81 """Delete a short URL.""" 82 await self._http.post("squid-api/v1/web/deleteShortUrl", {"id": url_id}) 83 84 async def delete_short_urls(self, url_ids: list[str]) -> None: 85 """Delete multiple short URLs.""" 86 await self._http.post("squid-api/v1/web/deleteShortUrls", {"ids": url_ids})
Web utilities: AI search, URL content, short URLs.
22 async def ai_search( 23 self, query: str, allowed_domains: list[str] | None = None 24 ) -> WebAiSearchResponse: 25 """Perform an AI-powered web search. 26 27 When allowed_domains is provided, the search is restricted to those domains 28 (subdomains included) and every cited URL belongs to one of them. 29 30 Returns WebAiSearchResponse with 'markdownText' and 'citedUrls'. 31 """ 32 body: dict[str, object] = {"query": query} 33 if allowed_domains is not None: 34 body["allowedDomains"] = allowed_domains 35 return await self._http.post("squid-api/v1/web/aiSearch", body)
Perform an AI-powered web search.
When allowed_domains is provided, the search is restricted to those domains (subdomains included) and every cited URL belongs to one of them.
Returns WebAiSearchResponse with 'markdownText' and 'citedUrls'.
37 async def get_url_content(self, url: str) -> str: 38 """Fetch and extract content from a URL as markdown.""" 39 result = await self._http.post("squid-api/v1/web/getUrlContent", {"url": url}) 40 if isinstance(result, dict): 41 return result.get("markdownText", "") 42 return str(result) if result else ""
Fetch and extract content from a URL as markdown.
44 async def create_short_url( 45 self, 46 url: str, 47 *, 48 seconds_to_live: int | None = None, 49 file_extension: str | None = None, 50 ) -> WebShortUrlResponse: 51 """Create a short URL. 52 53 Returns WebShortUrlResponse with 'id', 'shortUrl', 'expiry'. 54 """ 55 body: dict = {"url": url} 56 if seconds_to_live is not None: 57 body["secondsToLive"] = seconds_to_live 58 if file_extension is not None: 59 body["fileExtension"] = file_extension 60 return await self._http.post("squid-api/v1/web/createShortUrl", body)
Create a short URL.
Returns WebShortUrlResponse with 'id', 'shortUrl', 'expiry'.
62 async def create_short_urls( 63 self, 64 urls: list[str], 65 *, 66 seconds_to_live: int | None = None, 67 file_extension: str | None = None, 68 ) -> WebShortUrlBulkResponse: 69 """Create multiple short URLs in bulk. 70 71 Returns WebShortUrlBulkResponse with 'ids', 'shortUrls', 'expiry'. 72 """ 73 body: dict = {"urls": urls} 74 if seconds_to_live is not None: 75 body["secondsToLive"] = seconds_to_live 76 if file_extension is not None: 77 body["fileExtension"] = file_extension 78 return await self._http.post("squid-api/v1/web/createShortUrls", body)
Create multiple short URLs in bulk.
Returns WebShortUrlBulkResponse with 'ids', 'shortUrls', 'expiry'.
689class WebShortUrlBulkResponse(TypedDict): 690 """Response from creating bulk short URLs.""" 691 692 ids: list[str] 693 shortUrls: list[str] 694 expiry: str
Response from creating bulk short URLs.
681class WebShortUrlResponse(TypedDict): 682 """Response from creating a short URL.""" 683 684 id: str 685 shortUrl: str 686 expiry: str
Response from creating a short URL.