uipath 2.1.49__py3-none-any.whl → 2.1.51__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- uipath/_cli/__init__.py +1 -0
- uipath/_cli/_evals/progress_reporter.py +36 -44
- uipath/_cli/cli_init.py +31 -0
- uipath/_resources/AGENTS.md +724 -0
- uipath/_services/__init__.py +2 -0
- uipath/_services/context_grounding_service.py +19 -24
- uipath/_services/entities_service.py +383 -0
- uipath/_services/jobs_service.py +3 -4
- uipath/_services/llm_gateway_service.py +3 -4
- uipath/_uipath.py +5 -0
- uipath/models/entities.py +286 -0
- {uipath-2.1.49.dist-info → uipath-2.1.51.dist-info}/METADATA +1 -1
- {uipath-2.1.49.dist-info → uipath-2.1.51.dist-info}/RECORD +16 -13
- {uipath-2.1.49.dist-info → uipath-2.1.51.dist-info}/WHEEL +0 -0
- {uipath-2.1.49.dist-info → uipath-2.1.51.dist-info}/entry_points.txt +0 -0
- {uipath-2.1.49.dist-info → uipath-2.1.51.dist-info}/licenses/LICENSE +0 -0
@@ -0,0 +1,724 @@
|
|
1
|
+
# AGENTS.md – Unified Guide for UiPath Workflows & Agentic Solutions
|
2
|
+
|
3
|
+
This document provides a comprehensive guide to building, testing, and deploying Python automations and intelligent agents on the UiPath platform using the `uipath-python` and `uipath-langchain-python` SDK, just like the agent present in this folder.
|
4
|
+
|
5
|
+
---
|
6
|
+
|
7
|
+
## 0) Local Environment Setup (with `uv`)
|
8
|
+
|
9
|
+
This project assumes you’re using [`uv`](https://github.com/astral-sh/uv) for fast Python installs, virtualenvs, and command execution.
|
10
|
+
|
11
|
+
### 0.1 Install Python & create a virtualenv
|
12
|
+
|
13
|
+
```bash
|
14
|
+
# Install a modern Python (adjust the version if you need)
|
15
|
+
uv python install 3.12
|
16
|
+
|
17
|
+
# Create a local virtual environment (uses the latest installed Python by default)
|
18
|
+
uv venv
|
19
|
+
```
|
20
|
+
|
21
|
+
> **Tip:** You don’t need to “activate” the venv if you use `uv run ...`, but if you prefer activation:
|
22
|
+
>
|
23
|
+
> - macOS/Linux: `source .venv/bin/activate`
|
24
|
+
> - Windows PowerShell: `.venv\Scripts\Activate.ps1`
|
25
|
+
|
26
|
+
### 0.2 Install dependencies
|
27
|
+
|
28
|
+
```bash
|
29
|
+
uv pip install -e .
|
30
|
+
```
|
31
|
+
|
32
|
+
### 0.3 Run the UiPath CLI via `uv`
|
33
|
+
|
34
|
+
Using `uv run` means you don’t have to activate the venv:
|
35
|
+
|
36
|
+
```bash
|
37
|
+
# Log in and write credentials to .env
|
38
|
+
uv run uipath auth
|
39
|
+
|
40
|
+
# Initialize (scans entrypoints and updates uipath.json)
|
41
|
+
uv run uipath init
|
42
|
+
|
43
|
+
# Interactive dev loop (recommended)
|
44
|
+
uv run uipath dev
|
45
|
+
|
46
|
+
# Non-interactive run of classic entrypoint
|
47
|
+
uv run uipath run main.py '{"message": "Hello from uv"}'
|
48
|
+
|
49
|
+
# If you exposed a compiled graph entrypoint called "agent"
|
50
|
+
# (name exposed in langgraph.json)
|
51
|
+
uv run uipath run agent '{"topic": "Quarterly sales"}'
|
52
|
+
```
|
53
|
+
|
54
|
+
## 1) Core Developer Workflow (CLI)
|
55
|
+
|
56
|
+
The **unified CLI** supports both classic automations and LangGraph agents.
|
57
|
+
|
58
|
+
### 1.1 Authenticate
|
59
|
+
|
60
|
+
```bash
|
61
|
+
uipath auth
|
62
|
+
```
|
63
|
+
|
64
|
+
- Opens a browser login and writes credentials to `.env`.
|
65
|
+
- Required before local runs or publishing.
|
66
|
+
|
67
|
+
### 1.2 Initialize
|
68
|
+
|
69
|
+
```bash
|
70
|
+
uipath init
|
71
|
+
|
72
|
+
```
|
73
|
+
|
74
|
+
- Scans the classic entrypoint (`main.py`) and creates/updates `uipath.json` with **input/output schema** and **resource bindings**.
|
75
|
+
- Re‑run when you change function signatures, add Assets/Queues/Buckets, or new graph entrypoints.
|
76
|
+
|
77
|
+
### 1.3 Local Run & Debug
|
78
|
+
|
79
|
+
```bash
|
80
|
+
# Interactive development mode (recommended)
|
81
|
+
uipath dev
|
82
|
+
|
83
|
+
# Non‑interactive quick runs
|
84
|
+
uipath run main.py '{"message": "Hello from the CLI"}'
|
85
|
+
# For a compiled graph
|
86
|
+
uipath run agent '{"topic": "Quarterly sales"}'
|
87
|
+
```
|
88
|
+
|
89
|
+
- `dev` shows live logs, traces, and chat history.
|
90
|
+
|
91
|
+
### 1.4 Package, Publish, Deploy
|
92
|
+
|
93
|
+
```bash
|
94
|
+
uipath pack
|
95
|
+
uipath publish
|
96
|
+
uipath deploy
|
97
|
+
```
|
98
|
+
|
99
|
+
- `deploy` is a wrapper that packs and publishes to your Orchestrator feed.
|
100
|
+
- Use per‑environment pipelines (Dev → Test → Prod folders/tenants).
|
101
|
+
|
102
|
+
### 1.5 Other Useful Commands
|
103
|
+
|
104
|
+
```bash
|
105
|
+
uipath invoke # Execute a process remotely (when configured)
|
106
|
+
uipath eval # Run evaluation scenarios for agents
|
107
|
+
uipath --help # Discover flags and subcommands
|
108
|
+
```
|
109
|
+
|
110
|
+
---
|
111
|
+
|
112
|
+
## 2) Environment, Credentials & Configuration
|
113
|
+
|
114
|
+
Both SDKs read their configuration from **environment variables** (directly, or via `.env` loaded by `python-dotenv`).
|
115
|
+
|
116
|
+
### 2.1 Minimal local `.env`
|
117
|
+
|
118
|
+
```bash
|
119
|
+
UIPATH_URL="https://cloud.uipath.com/ORG/TENANT"
|
120
|
+
UIPATH_ACCESS_TOKEN="your-token"
|
121
|
+
|
122
|
+
# Common defaults
|
123
|
+
UIPATH_FOLDER_PATH="Shared"
|
124
|
+
```
|
125
|
+
|
126
|
+
> **Best practice:** Commit `.env.example` (documenting required vars) but never commit `.env`.
|
127
|
+
|
128
|
+
### 2.3 Loading configuration in code
|
129
|
+
|
130
|
+
```python
|
131
|
+
from dotenv import load_dotenv
|
132
|
+
from uipath import UiPath
|
133
|
+
from uipath.models.errors import BaseUrlMissingError, SecretMissingError
|
134
|
+
|
135
|
+
load_dotenv()
|
136
|
+
try:
|
137
|
+
sdk = UiPath()
|
138
|
+
except (BaseUrlMissingError, SecretMissingError) as e:
|
139
|
+
raise SystemExit(f"Config error: {e}. Run 'uipath auth' or set env vars.")
|
140
|
+
```
|
141
|
+
|
142
|
+
---
|
143
|
+
|
144
|
+
## 3) Classic Automation Track (Python SDK, `uipath`)
|
145
|
+
|
146
|
+
### 3.1 Entrypoint shape (Pydantic IO strongly recommended)
|
147
|
+
|
148
|
+
```python
|
149
|
+
# src/main.py
|
150
|
+
from pydantic import BaseModel
|
151
|
+
from typing import Optional
|
152
|
+
from dotenv import load_dotenv
|
153
|
+
from uipath import UiPath
|
154
|
+
|
155
|
+
load_dotenv()
|
156
|
+
|
157
|
+
class AutomationInput(BaseModel):
|
158
|
+
customer_id: str
|
159
|
+
message: str
|
160
|
+
|
161
|
+
class AutomationOutput(BaseModel):
|
162
|
+
status: str
|
163
|
+
confirmation_code: Optional[str] = None
|
164
|
+
|
165
|
+
def main(input: AutomationInput) -> AutomationOutput:
|
166
|
+
sdk = UiPath()
|
167
|
+
cfg = sdk.assets.retrieve(name="GlobalConfig")
|
168
|
+
print(f"Using API URL from asset: {cfg.value}")
|
169
|
+
return AutomationOutput(status="Success", confirmation_code="ABC-123")
|
170
|
+
```
|
171
|
+
|
172
|
+
### 3.2 Core recipes
|
173
|
+
|
174
|
+
#### Execute a child process
|
175
|
+
|
176
|
+
```python
|
177
|
+
import time
|
178
|
+
from dotenv import load_dotenv
|
179
|
+
from uipath import UiPath
|
180
|
+
|
181
|
+
load_dotenv()
|
182
|
+
sdk = UiPath()
|
183
|
+
job = sdk.processes.invoke(
|
184
|
+
name="Process_To_Run_In_Finance",
|
185
|
+
input_arguments={"customer_id": 12345},
|
186
|
+
folder_path="Finance",
|
187
|
+
)
|
188
|
+
while job.state in ("Pending", "Running"):
|
189
|
+
time.sleep(5)
|
190
|
+
job = sdk.jobs.retrieve(key=job.key)
|
191
|
+
print("State:", job.state, "Output:", job.output_arguments)
|
192
|
+
```
|
193
|
+
|
194
|
+
#### Assets – configuration & credentials
|
195
|
+
|
196
|
+
```python
|
197
|
+
from uipath import UiPath
|
198
|
+
|
199
|
+
sdk = UiPath()
|
200
|
+
plain = sdk.assets.retrieve(name="My_App_Config")
|
201
|
+
print("Endpoint:", plain.value)
|
202
|
+
|
203
|
+
try:
|
204
|
+
cred = sdk.assets.retrieve_credential(name="My_App_Credential")
|
205
|
+
print("Got credential username:", cred.username)
|
206
|
+
except ValueError as e:
|
207
|
+
print("Credential unavailable in non‑robot context:", e)
|
208
|
+
```
|
209
|
+
|
210
|
+
#### Queues – transactional work
|
211
|
+
|
212
|
+
```python
|
213
|
+
from uipath import UiPath
|
214
|
+
|
215
|
+
sdk = UiPath()
|
216
|
+
QUEUE = "InvoiceProcessing"
|
217
|
+
sdk.queues.create_item(
|
218
|
+
name=QUEUE,
|
219
|
+
specific_content={"invoice_id": "INV-9876", "amount": 450.75, "vendor": "Supplier Inc."},
|
220
|
+
priority="High",
|
221
|
+
)
|
222
|
+
trx = sdk.queues.create_transaction_item(name=QUEUE)
|
223
|
+
if trx:
|
224
|
+
try:
|
225
|
+
# ... process trx.specific_content ...
|
226
|
+
sdk.queues.complete_transaction_item(trx.id, {"status": "Successful", "message": "OK"})
|
227
|
+
except Exception as e:
|
228
|
+
sdk.queues.complete_transaction_item(trx.id, {"status": "Failed", "is_successful": False, "processing_exception": str(e)})
|
229
|
+
```
|
230
|
+
|
231
|
+
#### Buckets – file management
|
232
|
+
|
233
|
+
```python
|
234
|
+
from uipath import UiPath
|
235
|
+
|
236
|
+
sdk = UiPath()
|
237
|
+
with open("report.pdf", "w") as f:
|
238
|
+
f.write("sample report")
|
239
|
+
|
240
|
+
sdk.buckets.upload(name="MonthlyReports", source_path="report.pdf", blob_file_path="2024/July/report.pdf")
|
241
|
+
sdk.buckets.download(name="InputFiles", blob_file_path="data/customers.xlsx", destination_path="local_customers.xlsx")
|
242
|
+
```
|
243
|
+
|
244
|
+
#### Context Grounding – RAG
|
245
|
+
|
246
|
+
```python
|
247
|
+
from uipath import UiPath
|
248
|
+
|
249
|
+
async def main(input: dict):
|
250
|
+
sdk = UiPath()
|
251
|
+
q = input.get("query")
|
252
|
+
hits = sdk.context_grounding.search(name="Internal_Wiki", query=q, number_of_results=3)
|
253
|
+
context = "\n".join([h.content for h in hits])
|
254
|
+
enriched = f"Context:\n{context}\n\nAnswer: {q}"
|
255
|
+
resp = await sdk.llm.chat_completions(model="gpt-4o-mini-2024-07-18", messages=[{"role": "user", "content": enriched}])
|
256
|
+
return {"answer": resp.choices[0].message.content}
|
257
|
+
```
|
258
|
+
|
259
|
+
#### Event triggers – Integration Service
|
260
|
+
|
261
|
+
```python
|
262
|
+
from pydantic import BaseModel
|
263
|
+
from uipath import UiPath
|
264
|
+
from uipath.models import EventArguments
|
265
|
+
|
266
|
+
class Output(BaseModel):
|
267
|
+
status: str
|
268
|
+
summary: str
|
269
|
+
|
270
|
+
def main(input: EventArguments) -> Output:
|
271
|
+
sdk = UiPath()
|
272
|
+
payload = sdk.connections.retrieve_event_payload(input)
|
273
|
+
if "event" in payload and "text" in payload["event"]:
|
274
|
+
txt = payload["event"]["text"]
|
275
|
+
user = payload["event"].get("user", "Unknown")
|
276
|
+
summ = sdk.llm.chat(prompt=f"Summarize from {user}: {txt}", model="gpt-4")
|
277
|
+
return Output(status="Processed", summary=getattr(summ, "content", str(summ)))
|
278
|
+
return Output(status="Skipped", summary="Not a Slack message event")
|
279
|
+
```
|
280
|
+
|
281
|
+
#### Passing files between jobs – attachments
|
282
|
+
|
283
|
+
```python
|
284
|
+
from uipath import UiPath
|
285
|
+
from uipath.models import InvokeProcess
|
286
|
+
|
287
|
+
def main(input_args: dict):
|
288
|
+
sdk = UiPath()
|
289
|
+
csv = "id,name\n1,Alice\n2,Bob"
|
290
|
+
att_key = sdk.jobs.create_attachment(name="processed.csv", content=csv)
|
291
|
+
return InvokeProcess(name="LoadDataToSystem", input_arguments={"dataFileKey": str(att_key)})
|
292
|
+
```
|
293
|
+
|
294
|
+
---
|
295
|
+
|
296
|
+
## 4) Agentic Track (LangGraph/LangChain SDK, `uipath-langchain`)
|
297
|
+
|
298
|
+
### 4.1 Quick start – chat model
|
299
|
+
|
300
|
+
```python
|
301
|
+
from uipath_langchain.chat import UiPathChat
|
302
|
+
from langchain_core.messages import HumanMessage
|
303
|
+
|
304
|
+
chat = UiPathChat(model="gpt-4o-2024-08-06", max_retries=3)
|
305
|
+
print(chat.invoke([HumanMessage(content="Hello")]).content)
|
306
|
+
```
|
307
|
+
|
308
|
+
### 4.2 Simple graph example
|
309
|
+
|
310
|
+
`graph = builder.compile()` is enough for the agent to run with `uipath run agent '{"topic": "Quarterly sales"}`
|
311
|
+
|
312
|
+
```python
|
313
|
+
from langchain_core.messages import HumanMessage, SystemMessage
|
314
|
+
from langgraph.graph import START, StateGraph, END
|
315
|
+
from uipath_langchain.chat import UiPathChat
|
316
|
+
from pydantic import BaseModel
|
317
|
+
import os
|
318
|
+
|
319
|
+
llm = UiPathChat(model="gpt-4o-mini-2024-07-18")
|
320
|
+
|
321
|
+
class GraphState(BaseModel):
|
322
|
+
topic: str
|
323
|
+
|
324
|
+
class GraphOutput(BaseModel):
|
325
|
+
report: str
|
326
|
+
|
327
|
+
async def generate_report(state: GraphState) -> GraphOutput:
|
328
|
+
system_prompt = "You are a report generator. Please provide a brief report based on the given topic."
|
329
|
+
output = await llm.ainvoke([SystemMessage(system_prompt), HumanMessage(state.topic)])
|
330
|
+
return GraphOutput(report=output.content)
|
331
|
+
|
332
|
+
builder = StateGraph(GraphState, output=GraphOutput)
|
333
|
+
|
334
|
+
builder.add_node("generate_report", generate_report)
|
335
|
+
|
336
|
+
builder.add_edge(START, "generate_report")
|
337
|
+
builder.add_edge("generate_report", END)
|
338
|
+
|
339
|
+
graph = builder.compile()
|
340
|
+
```
|
341
|
+
|
342
|
+
### 4.3 ReAct‑style agent with tools
|
343
|
+
|
344
|
+
```python
|
345
|
+
from langgraph.graph import StateGraph, START, END
|
346
|
+
from langgraph.prebuilt import create_react_agent
|
347
|
+
from langchain_tavily import TavilySearch
|
348
|
+
from uipath_langchain.chat import UiPathChat
|
349
|
+
from pydantic import BaseModel
|
350
|
+
|
351
|
+
class GraphState(BaseModel):
|
352
|
+
company_name: str
|
353
|
+
|
354
|
+
tavily = TavilySearch(max_results=5)
|
355
|
+
llm = UiPathChat(model="gpt-4o-2024-08-06")
|
356
|
+
agent = create_react_agent(llm, tools=[tavily], prompt="You are a research assistant.")
|
357
|
+
|
358
|
+
builder = StateGraph(GraphState)
|
359
|
+
builder.add_node("research", agent)
|
360
|
+
builder.add_edge(START, "research")
|
361
|
+
builder.add_edge("research", END)
|
362
|
+
|
363
|
+
graph = builder.compile()
|
364
|
+
```
|
365
|
+
|
366
|
+
### 4.4 RAG – Context Grounding vector store & retriever
|
367
|
+
|
368
|
+
```python
|
369
|
+
from uipath_langchain.vectorstores import ContextGroundingVectorStore
|
370
|
+
from uipath_langchain.chat import UiPathAzureChatOpenAI
|
371
|
+
from langchain_core.prompts import ChatPromptTemplate
|
372
|
+
|
373
|
+
vs = ContextGroundingVectorStore(index_name="my_knowledge_base")
|
374
|
+
retriever = vs.as_retriever(search_kwargs={"k": 3})
|
375
|
+
|
376
|
+
prompt = ChatPromptTemplate.from_template("""Answer from context:
|
377
|
+
{context}
|
378
|
+
Question: {question}
|
379
|
+
""")
|
380
|
+
llm = UiPathAzureChatOpenAI(model="gpt-4o-2024-08-06")
|
381
|
+
|
382
|
+
docs = retriever.invoke("Vacation policy?")
|
383
|
+
print(llm.invoke(prompt.format(context=docs, question="Vacation policy? ")).content)
|
384
|
+
```
|
385
|
+
|
386
|
+
### 4.5 Embeddings & structured outputs
|
387
|
+
|
388
|
+
```python
|
389
|
+
from uipath_langchain.embeddings import UiPathAzureOpenAIEmbeddings
|
390
|
+
from uipath_langchain.chat import UiPathChat
|
391
|
+
from pydantic import BaseModel, Field
|
392
|
+
|
393
|
+
emb = UiPathAzureOpenAIEmbeddings(model="text-embedding-3-large")
|
394
|
+
vec = emb.embed_query("remote work policy")
|
395
|
+
|
396
|
+
class EmailRule(BaseModel):
|
397
|
+
rule_name: str = Field(description="Name of the rule")
|
398
|
+
conditions: dict = Field(description="Rule conditions")
|
399
|
+
target_folder: str = Field(description="Target folder")
|
400
|
+
|
401
|
+
schema_chat = UiPathChat(model="gpt-4o-2024-08-06").with_structured_output(EmailRule)
|
402
|
+
rule = schema_chat.invoke("Create a rule to move emails from noreply@company.com to Archive")
|
403
|
+
```
|
404
|
+
|
405
|
+
### 4.6 Observability – Async tracer
|
406
|
+
|
407
|
+
```python
|
408
|
+
from uipath_langchain.tracers import AsyncUiPathTracer
|
409
|
+
from uipath_langchain.chat import UiPathChat
|
410
|
+
|
411
|
+
tracer = AsyncUiPathTracer(action_name="my_action", action_id="unique_id")
|
412
|
+
chat = UiPathChat(model="gpt-4o-2024-08-06", callbacks=[tracer])
|
413
|
+
```
|
414
|
+
|
415
|
+
---
|
416
|
+
|
417
|
+
## 5) LLM Gateway – Two ways to call models
|
418
|
+
|
419
|
+
### 5.1 OpenAI‑compatible path
|
420
|
+
|
421
|
+
```python
|
422
|
+
from uipath import UiPath
|
423
|
+
sdk = UiPath()
|
424
|
+
resp = sdk.llm_openai.chat.completions.create(
|
425
|
+
model="gpt-4",
|
426
|
+
messages=[{"role": "user", "content": "Summarize this invoice"}],
|
427
|
+
)
|
428
|
+
print(resp.choices[0].message.content)
|
429
|
+
```
|
430
|
+
|
431
|
+
### 5.2 Normalized UiPath LLM path
|
432
|
+
|
433
|
+
```python
|
434
|
+
from uipath import UiPath
|
435
|
+
sdk = UiPath()
|
436
|
+
answer = sdk.llm.chat(prompt="Analyze customer feedback", model="gpt-4")
|
437
|
+
print(answer.content if hasattr(answer, "content") else answer)
|
438
|
+
```
|
439
|
+
|
440
|
+
---
|
441
|
+
|
442
|
+
## 6) Testing, Evaluation & Quality Gates
|
443
|
+
|
444
|
+
- **Unit tests**: Pure functions in `src/` and graph nodes in `graphs/`.
|
445
|
+
- **E2E tests**: Use `uipath run` against local mocks or a Dev folder tenant.
|
446
|
+
- **Evaluations**: For agent behaviors, leverage `uipath eval` scenarios to benchmark prompt/graph changes.
|
447
|
+
- **Static checks**: `ruff`, `pyright`/`mypy` with type‑strict public APIs.
|
448
|
+
|
449
|
+
Minimal sanity check:
|
450
|
+
|
451
|
+
```python
|
452
|
+
import importlib.metadata, sys
|
453
|
+
print("uipath:", importlib.metadata.version("uipath"))
|
454
|
+
print("python:", sys.version)
|
455
|
+
```
|
456
|
+
|
457
|
+
## 8) Security, Secrets & Governance
|
458
|
+
|
459
|
+
- **Never** commit secrets. Use Secret Manager / GitHub Actions secrets.
|
460
|
+
- Scope tokens to least privilege; rotate regularly.
|
461
|
+
- For **credential assets**, prefer Action Center/Robot context retrieval over plain text.
|
462
|
+
- Enable **telemetry** and **tracing** for auditability.
|
463
|
+
|
464
|
+
---
|
465
|
+
|
466
|
+
## 9) Operational Patterns & Pitfalls
|
467
|
+
|
468
|
+
- **Folder context**: Prefer `folder_path`/`folder_key` explicitly in critical calls.
|
469
|
+
- **Idempotency**: For queues and bucket uploads, include natural keys and conflict handling.
|
470
|
+
- **Backpressure**: Poll jobs with exponential backoff; avoid tight loops.
|
471
|
+
- **Timeouts**: Raise `UIPATH_TIMEOUT_SECONDS` for large payloads.
|
472
|
+
- **Version pins**: For LangGraph, stay within `>=0.5,<0.7` range.
|
473
|
+
|
474
|
+
---
|
475
|
+
|
476
|
+
## 10) Merged API Surface
|
477
|
+
|
478
|
+
### 10.1 `uipath` (Python SDK)
|
479
|
+
|
480
|
+
#### Processes
|
481
|
+
|
482
|
+
- **`sdk.processes.invoke(name, input_arguments=None, folder_key=None, folder_path=None) -> Job`**
|
483
|
+
Start a process by **Release name**. Returns a `Job` with attributes like `.key`, `.state`, `.start_time`, `.end_time`, `.output_arguments` (string or JSON), and `.faulted_reason` when applicable.
|
484
|
+
_Common errors_: `httpx.HTTPStatusError 404 /Releases` (bad name or wrong folder), `403 Forbidden` (insufficient RBAC).
|
485
|
+
_Example:_
|
486
|
+
|
487
|
+
```python
|
488
|
+
job = sdk.processes.invoke("ACME_Invoice_Load", {"batch_id": "B-42"}, folder_path="Finance")
|
489
|
+
while job.state in ("Pending", "Running"):
|
490
|
+
await asyncio.sleep(3)
|
491
|
+
job = sdk.jobs.retrieve(job.key, folder_path="Finance")
|
492
|
+
if job.state == "Successful":
|
493
|
+
print("Output:", job.output_arguments)
|
494
|
+
else:
|
495
|
+
print("Failed:", job.faulted_reason)
|
496
|
+
```
|
497
|
+
|
498
|
+
- **`sdk.processes.invoke_async(...) -> Job`** – Fire‑and‑forget; same return as `invoke` but do not block.
|
499
|
+
|
500
|
+
#### Jobs
|
501
|
+
|
502
|
+
- **`sdk.jobs.retrieve(job_key, folder_key=None, folder_path=None) -> Job`** – Refresh job state and metadata.
|
503
|
+
- **`sdk.jobs.resume(inbox_id, job_id, folder_key=None, folder_path=None, payload=None) -> None`** – Resume a suspended job (HITL continuation).
|
504
|
+
- **`sdk.jobs.extract_output(job) -> Optional[str]`** – Convenience helper to get the output string.
|
505
|
+
- **Attachments API**
|
506
|
+
- `sdk.jobs.list_attachments(job_key, folder_key=None, folder_path=None) -> list[str]`
|
507
|
+
- `sdk.jobs.create_attachment(name, content=None, source_path=None, job_key=None, category=None, folder_key=None, folder_path=None) -> uuid.UUID`
|
508
|
+
- `sdk.jobs.link_attachment(attachment_key, job_key, category=None, folder_key=None, folder_path=None) -> None`
|
509
|
+
_Example:_
|
510
|
+
```python
|
511
|
+
key = sdk.jobs.create_attachment("summary.csv", content="id,val\n1,9")
|
512
|
+
sdk.jobs.link_attachment(key, job.key, category="Output")
|
513
|
+
for att in sdk.jobs.list_attachments(job.key):
|
514
|
+
print("Attachment:", att)
|
515
|
+
```
|
516
|
+
|
517
|
+
#### Assets
|
518
|
+
|
519
|
+
- **`sdk.assets.retrieve(name, folder_key=None, folder_path=None) -> Asset | UserAsset`** – Read scalar/JSON assets; access `.value`.
|
520
|
+
- **`sdk.assets.retrieve_credential(name, folder_key=None, folder_path=None)`** – Robot‑only; provides `.username` and `.password`.
|
521
|
+
- **`sdk.assets.update(robot_asset, folder_key=None, folder_path=None) -> Response`** – Update value (admin required).
|
522
|
+
_Tips_: Keep secrets in **Credential** assets. For per‑environment config, store by folder and pass `folder_path` explicitly.
|
523
|
+
|
524
|
+
#### Queues
|
525
|
+
|
526
|
+
- **`sdk.queues.create_item(name, specific_content: dict, priority='Normal', reference=None, due_date=None, ... ) -> Response`** – Enqueue work. Consider setting a **`reference`** to ensure idempotency.
|
527
|
+
- **`sdk.queues.create_transaction_item(name, no_robot: bool = False) -> TransactionItem | None`** – Claim a transaction for processing. Returned item has `.id`, `.specific_content`, `.reference`.
|
528
|
+
- **`sdk.queues.update_progress_of_transaction_item(transaction_key, progress: str) -> Response`** – Heartbeat/progress note.
|
529
|
+
- **`sdk.queues.complete_transaction_item(transaction_key, result: dict) -> Response`** – Mark result and, on failure, include `processing_exception`.
|
530
|
+
- **`sdk.queues.list_items(status=None, reference=None, top=100, ... ) -> Response`** – Filter queue contents.
|
531
|
+
_Example:_
|
532
|
+
```python
|
533
|
+
trx = sdk.queues.create_transaction_item("InvoiceProcessing")
|
534
|
+
if trx:
|
535
|
+
try:
|
536
|
+
# process trx.specific_content...
|
537
|
+
sdk.queues.complete_transaction_item(trx.id, {"status": "Successful", "message": "OK"})
|
538
|
+
except Exception as e:
|
539
|
+
sdk.queues.complete_transaction_item(trx.id, {
|
540
|
+
"status": "Failed", "is_successful": False, "processing_exception": str(e)
|
541
|
+
})
|
542
|
+
```
|
543
|
+
|
544
|
+
#### Buckets (Storage)
|
545
|
+
|
546
|
+
- **`sdk.buckets.upload(name, blob_file_path, source_path=None, content=None, content_type=None, folder_key=None, folder_path=None) -> None`** – Upload from disk or in‑memory `content`.
|
547
|
+
- **`sdk.buckets.download(name, blob_file_path, destination_path, folder_key=None, folder_path=None) -> None`** – Save a blob to local path.
|
548
|
+
- **`sdk.buckets.retrieve(name, key=None, folder_key=None, folder_path=None) -> Bucket`** – Inspect bucket metadata.
|
549
|
+
_Tip_: Use MIME `content_type` for correct downstream handling (e.g., `application/pdf`, `text/csv`).
|
550
|
+
|
551
|
+
#### Actions (Action Center)
|
552
|
+
|
553
|
+
- **`sdk.actions.create(title=None, data=None, app_name=None, app_key=None, app_folder_path=None, app_folder_key=None, app_version=None, assignee=None) -> Action`**
|
554
|
+
- **`sdk.actions.retrieve(action_key, app_folder_path=None, app_folder_key=None) -> Action`**
|
555
|
+
_Async variants available (`create_async`)._
|
556
|
+
_Pattern_: Create → return `WaitAction` from your `main()` → human completes → automation resumes via `jobs.resume` with payload.
|
557
|
+
|
558
|
+
#### Context Grounding (RAG)
|
559
|
+
|
560
|
+
- **`sdk.context_grounding.search(name, query, number_of_results=5, folder_key=None, folder_path=None) -> list[ContextGroundingQueryResponse]`** – Retrieve top‑k chunks (`.content`, `.source`).
|
561
|
+
- **`sdk.context_grounding.add_to_index(name, blob_file_path=None, content_type=None, content=None, source_path=None, ingest_data=True, folder_key=None, folder_path=None) -> None`** – Add docs.
|
562
|
+
- **`sdk.context_grounding.retrieve(name, folder_key=None, folder_path=None) -> ContextGroundingIndex`** – Inspect index.
|
563
|
+
- **`sdk.context_grounding.ingest_data(index, folder_key=None, folder_path=None) -> None`**, **`delete_index(index, ...)`** – Bulk ops.
|
564
|
+
_Example:_
|
565
|
+
```python
|
566
|
+
hits = sdk.context_grounding.search("Internal_Wiki", "vacation policy", 3)
|
567
|
+
ctx = "\n".join(h.content for h in hits)
|
568
|
+
answer = await sdk.llm.chat_completions(model="gpt-4o-mini-2024-07-18",
|
569
|
+
messages=[{"role":"user","content": f"Use this context:\n{ctx}\n\nQ: What is our policy?"}])
|
570
|
+
```
|
571
|
+
|
572
|
+
#### Connections (Integration Service)
|
573
|
+
|
574
|
+
- **`sdk.connections.retrieve(key) -> Connection`** – Connection metadata.
|
575
|
+
- **`sdk.connections.retrieve_token(key) -> ConnectionToken`** – OAuth token passthrough.
|
576
|
+
- **`sdk.connections.retrieve_event_payload(event_args) -> dict`** – Get full trigger payload for event‑driven agents.
|
577
|
+
|
578
|
+
#### Attachments (generic)
|
579
|
+
|
580
|
+
- **`sdk.attachments.upload(name, content=None, source_path=None, folder_key=None, folder_path=None) -> uuid.UUID`**
|
581
|
+
- **`sdk.attachments.download(key, destination_path, folder_key=None, folder_path=None) -> str`**
|
582
|
+
- **`sdk.attachments.delete(key, folder_key=None, folder_path=None) -> None`**
|
583
|
+
|
584
|
+
#### Folders
|
585
|
+
|
586
|
+
- **`sdk.folders.retrieve_key(folder_path) -> str | None`** – Resolve a path to folder key for scoping.
|
587
|
+
|
588
|
+
#### LLM Gateway
|
589
|
+
|
590
|
+
- **Normalized path**:
|
591
|
+
- `sdk.llm.chat_completions(model, messages, max_tokens=None, temperature=None, tools=None, tool_choice=None, ...) -> ChatCompletion`
|
592
|
+
- **OpenAI‑compatible path**:
|
593
|
+
- `sdk.llm_openai.chat.completions.create(model, messages, max_tokens=None, temperature=None, ...) -> ChatCompletion`
|
594
|
+
- `sdk.llm_openai.embeddings.create(input, embedding_model, openai_api_version=None) -> Embeddings`
|
595
|
+
_Tip_: Prefer **normalized** for UiPath‑first features; use **OpenAI‑compatible** to reuse LC/third‑party clients unchanged.
|
596
|
+
|
597
|
+
#### Low‑level HTTP
|
598
|
+
|
599
|
+
- **`sdk.api_client.request(method, url, scoped=True, infer_content_type=True, **kwargs) -> Response`\*\*
|
600
|
+
- **`sdk.api_client.request_async(...) -> Response`**
|
601
|
+
_Use cases_: custom endpoints, preview APIs, or troubleshooting raw requests.
|
602
|
+
|
603
|
+
---
|
604
|
+
|
605
|
+
### 10.2 `uipath-langchain` (LangGraph SDK)
|
606
|
+
|
607
|
+
#### Chat Models
|
608
|
+
|
609
|
+
- **`uipath_langchain.chat.UiPathChat`** (normalized) & **`UiPathAzureChatOpenAI`** (Azure passthrough)
|
610
|
+
**Init (common):** `model='gpt-4o-2024-08-06'`, `temperature`, `max_tokens`, `top_p`, `n`, `streaming=False`, `max_retries=2`, `request_timeout=None`, `callbacks=None`, `verbose=False`
|
611
|
+
**Messages:** `langchain_core.messages` (`SystemMessage`, `HumanMessage`, `AIMessage`) or plain string.
|
612
|
+
**Methods:**
|
613
|
+
|
614
|
+
- `invoke(messages | str) -> AIMessage` (sync)
|
615
|
+
- `ainvoke(messages | str) -> AIMessage` (async)
|
616
|
+
- `astream(messages)` → async generator of chunks (for streaming UIs)
|
617
|
+
- `with_structured_output(pydantic_model)` → parsed/validated output object
|
618
|
+
_Examples:_
|
619
|
+
|
620
|
+
```python
|
621
|
+
chat = UiPathChat(model="gpt-4o-2024-08-06")
|
622
|
+
print(chat.invoke("Say hi").content)
|
623
|
+
|
624
|
+
class Answer(BaseModel):
|
625
|
+
text: str
|
626
|
+
score: float
|
627
|
+
|
628
|
+
tool_chat = chat.with_structured_output(Answer)
|
629
|
+
parsed = tool_chat.invoke("Return a JSON with text and score")
|
630
|
+
```
|
631
|
+
|
632
|
+
#### Embeddings
|
633
|
+
|
634
|
+
- **`uipath_langchain.embeddings.UiPathAzureOpenAIEmbeddings`**
|
635
|
+
- `embed_documents(list[str]) -> list[list[float]]`
|
636
|
+
- `embed_query(str) -> list[float]`
|
637
|
+
_Params:_ `model='text-embedding-3-large'`, `dimensions=None`, `chunk_size=1000`, `max_retries=2`, `request_timeout=None`.
|
638
|
+
|
639
|
+
#### Vector Store (Context Grounding)
|
640
|
+
|
641
|
+
- **`uipath_langchain.vectorstores.ContextGroundingVectorStore(index_name, folder_path=None, uipath_sdk=None)`**
|
642
|
+
- `similarity_search(query, k=4) -> list[Document]`
|
643
|
+
- `similarity_search_with_score(query, k=4) -> list[tuple[Document, float]]`
|
644
|
+
- `similarity_search_with_relevance_scores(query, k=4, score_threshold=None) -> list[tuple[Document, float]]`
|
645
|
+
- `.as_retriever(search_kwargs={'k': 3}) -> BaseRetriever`
|
646
|
+
_Document fields_: `.page_content`, `.metadata` (source, uri, created_at).
|
647
|
+
|
648
|
+
#### Retriever
|
649
|
+
|
650
|
+
- **`uipath_langchain.retrievers.ContextGroundingRetriever(index_name, folder_path=None, folder_key=None, uipath_sdk=None, number_of_results=10)`**
|
651
|
+
- `invoke(query) -> list[Document]` (sync/async)
|
652
|
+
_Tip_: Use retriever in LC chains/graphs for clean separation of concerns.
|
653
|
+
|
654
|
+
#### Tracing / Observability
|
655
|
+
|
656
|
+
- **`uipath_langchain.tracers.AsyncUiPathTracer(action_name=None, action_id=None, context=None)`**
|
657
|
+
Add to `callbacks=[tracer]` on any LC runnable to capture spans/metadata into UiPath.
|
658
|
+
|
659
|
+
#### Agent Building with LangGraph
|
660
|
+
|
661
|
+
- **`langgraph.prebuilt.create_react_agent(llm, tools, prompt=None, **kwargs) -> Runnable`\*\* – Get a practical ReAct agent quickly.
|
662
|
+
- **`langgraph.graph.StateGraph`**
|
663
|
+
- `add_node(name, fn)` – Node is callable (sync/async) receiving/returning your `State` model.
|
664
|
+
- `add_edge(src, dst)` – Connect nodes (`START` and `END` available).
|
665
|
+
- `compile() -> Graph` – Freeze DAG for execution.
|
666
|
+
_Pattern:_ use nodes for **tool‑use**, **HITL interrupt**, **routing**, and **post‑processing**.
|
667
|
+
|
668
|
+
---
|
669
|
+
|
670
|
+
## 11) Troubleshooting
|
671
|
+
|
672
|
+
**Classic**
|
673
|
+
|
674
|
+
- `SecretMissingError` / `BaseUrlMissingError` → run `uipath auth`, verify env.
|
675
|
+
- 404 for Releases/Assets → check object names and folder context.
|
676
|
+
- 403 Forbidden → token scopes; re‑authenticate or create proper OAuth app.
|
677
|
+
- Timeouts → network/proxy; verify `UIPATH_URL`.
|
678
|
+
|
679
|
+
**LangGraph**
|
680
|
+
|
681
|
+
- `ModuleNotFoundError: uipath_langchain` → `pip install uipath-langchain`.
|
682
|
+
- 401 Unauthorized → check `UIPATH_ACCESS_TOKEN` or OAuth pair.
|
683
|
+
- Version mismatch → ensure `langgraph>=0.5,<0.7`.
|
684
|
+
|
685
|
+
---
|
686
|
+
|
687
|
+
## 12) Glossary
|
688
|
+
|
689
|
+
- **Action Center (HITL)**: Human‑in‑the‑loop task approvals.
|
690
|
+
- **Assets**: Centralized config/secret storage.
|
691
|
+
- **Buckets**: Cloud file storage.
|
692
|
+
- **Context Grounding**: UiPath semantic indexing for RAG.
|
693
|
+
- **LLM Gateway**: UiPath’s model broker (normalized and OpenAI‑compatible).
|
694
|
+
- **Queues**: Transactional work management.
|
695
|
+
|
696
|
+
---
|
697
|
+
|
698
|
+
## 13) Checklists
|
699
|
+
|
700
|
+
**Before first run**
|
701
|
+
|
702
|
+
- [ ] `uipath auth`
|
703
|
+
- [ ] Populate `.env` and copy to teammates as `.env.example` template
|
704
|
+
- [ ] `uipath init` after defining `main()` and/or graphs
|
705
|
+
|
706
|
+
**Pre‑publish**
|
707
|
+
|
708
|
+
- [ ] Unit + E2E passing
|
709
|
+
- [ ] `uipath pack` clean
|
710
|
+
- [ ] Secrets in Assets / Connections, not in code
|
711
|
+
|
712
|
+
**Production readiness**
|
713
|
+
|
714
|
+
- [ ] Folder scoping & RBAC verified
|
715
|
+
- [ ] Tracing/Telemetry enabled
|
716
|
+
- [ ] Runbooks for failures, retries, backoff
|
717
|
+
|
718
|
+
---
|
719
|
+
|
720
|
+
## 14) Links
|
721
|
+
|
722
|
+
- Project README: `./README.md`
|
723
|
+
- UiPath Python SDK docs & samples: https://uipath.github.io/uipath-python/
|
724
|
+
- UiPath LangGraph SDK docs & samples: https://uipath.github.io/uipath-python/langchain/quick_start/
|