a2a-lite 0.2.4__tar.gz → 0.2.5__tar.gz

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.
Files changed (42) hide show
  1. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/PKG-INFO +57 -30
  2. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/README.md +56 -29
  3. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/pyproject.toml +1 -1
  4. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/.claude/settings.local.json +0 -0
  5. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/.gitignore +0 -0
  6. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/01_hello_world.py +0 -0
  7. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/02_calculator.py +0 -0
  8. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/03_async_agent.py +0 -0
  9. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/04_multi_agent/finance_agent.py +0 -0
  10. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/04_multi_agent/reporter_agent.py +0 -0
  11. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/04_multi_agent/run_demo.py +0 -0
  12. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/05_with_llm.py +0 -0
  13. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/06_pydantic_models.py +0 -0
  14. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/07_middleware.py +0 -0
  15. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/08_streaming.py +0 -0
  16. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/09_testing.py +0 -0
  17. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/10_file_handling.py +0 -0
  18. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/11_task_tracking.py +0 -0
  19. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/examples/12_with_auth.py +0 -0
  20. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/__init__.py +0 -0
  21. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/agent.py +0 -0
  22. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/auth.py +0 -0
  23. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/cli.py +0 -0
  24. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/decorators.py +0 -0
  25. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/executor.py +0 -0
  26. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/middleware.py +0 -0
  27. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/parts.py +0 -0
  28. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/streaming.py +0 -0
  29. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/tasks.py +0 -0
  30. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/testing.py +0 -0
  31. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/src/a2a_lite/utils.py +0 -0
  32. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/__init__.py +0 -0
  33. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_agent.py +0 -0
  34. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_auth.py +0 -0
  35. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_decorators.py +0 -0
  36. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_integration.py +0 -0
  37. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_middleware.py +0 -0
  38. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_parts.py +0 -0
  39. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_pydantic.py +0 -0
  40. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_tasks.py +0 -0
  41. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_testing.py +0 -0
  42. {a2a_lite-0.2.4 → a2a_lite-0.2.5}/tests/test_utils.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: a2a-lite
3
- Version: 0.2.4
3
+ Version: 0.2.5
4
4
  Summary: Simplified wrapper for Google's A2A Protocol SDK
5
5
  Author: A2A Lite Contributors
6
6
  License-Expression: MIT
@@ -29,11 +29,14 @@ Provides-Extra: oauth
29
29
  Requires-Dist: pyjwt[crypto]>=2.0; extra == 'oauth'
30
30
  Description-Content-Type: text/markdown
31
31
 
32
- # A2A Lite - Python
32
+ # A2A Lite Python
33
+
34
+ [![PyPI](https://img.shields.io/pypi/v/a2a-lite?label=PyPI&logo=pypi&logoColor=white)](https://pypi.org/project/a2a-lite/)
35
+ [![GitHub](https://img.shields.io/badge/GitHub-a2a--lite-blue?logo=github)](https://github.com/xvierd/a2a-lite)
33
36
 
34
37
  **Build A2A agents in 8 lines. Add features when you need them.**
35
38
 
36
- Wraps the official [A2A Python SDK](https://github.com/a2aproject/a2a-python) with a simple, intuitive API.
39
+ Wraps the official [A2A Python SDK](https://github.com/a2aproject/a2a-python) with a simple, decorator-based API. 100% protocol-compatible.
37
40
 
38
41
  ```python
39
42
  from a2a_lite import Agent
@@ -81,7 +84,7 @@ async def multiply(a: int, b: int) -> int:
81
84
  agent.run(port=8787)
82
85
  ```
83
86
 
84
- ### 2. Test it
87
+ ### 2. Test it (no HTTP needed)
85
88
 
86
89
  ```python
87
90
  from a2a_lite import Agent, AgentTestClient
@@ -97,7 +100,7 @@ result = client.call("add", a=2, b=3)
97
100
  assert result == 5
98
101
  ```
99
102
 
100
- ### 3. Call it
103
+ ### 3. Call it over the network
101
104
 
102
105
  ```bash
103
106
  curl -X POST http://localhost:8787/ \
@@ -120,7 +123,7 @@ curl -X POST http://localhost:8787/ \
120
123
 
121
124
  ## Progressive Complexity
122
125
 
123
- ### Level 1: Basic Skills
126
+ ### Level 1 Basic Skills
124
127
 
125
128
  ```python
126
129
  from a2a_lite import Agent
@@ -134,7 +137,7 @@ async def greet(name: str) -> str:
134
137
  agent.run()
135
138
  ```
136
139
 
137
- ### Level 2: Pydantic Models (Just Works)
140
+ ### Level 2 Pydantic Models
138
141
 
139
142
  Pass dicts from callers — they're auto-converted to Pydantic models:
140
143
 
@@ -160,7 +163,9 @@ async def count_users(users: List[User]) -> int:
160
163
  return len(users)
161
164
  ```
162
165
 
163
- ### Level 3: Streaming (Just Yield)
166
+ ### Level 3 Streaming
167
+
168
+ Just `yield` instead of `return`:
164
169
 
165
170
  ```python
166
171
  @agent.skill("chat", streaming=True)
@@ -169,7 +174,9 @@ async def chat(message: str):
169
174
  yield word + " "
170
175
  ```
171
176
 
172
- ### Level 4: Middleware
177
+ ### Level 4 Middleware
178
+
179
+ Cross-cutting concerns without touching skill code:
173
180
 
174
181
  ```python
175
182
  @agent.middleware
@@ -191,7 +198,9 @@ agent.add_middleware(rate_limit_middleware(max_per_minute=60))
191
198
  agent.add_middleware(retry_middleware(max_retries=3))
192
199
  ```
193
200
 
194
- ### Level 5: File Handling
201
+ ### Level 5 File Handling
202
+
203
+ Accept and return files through the A2A protocol:
195
204
 
196
205
  ```python
197
206
  from a2a_lite import FilePart
@@ -202,7 +211,9 @@ async def summarize(doc: FilePart) -> str:
202
211
  return f"Summary: {content[:100]}..."
203
212
  ```
204
213
 
205
- ### Level 6: Task Tracking
214
+ ### Level 6 Task Tracking
215
+
216
+ Long-running operations with progress updates:
206
217
 
207
218
  ```python
208
219
  from a2a_lite import TaskContext
@@ -212,14 +223,14 @@ agent = Agent(name="Bot", description="A bot", task_store="memory")
212
223
  @agent.skill("process")
213
224
  async def process(data: str, task: TaskContext) -> str:
214
225
  await task.update("working", "Starting...", progress=0.0)
215
-
216
226
  for i in range(10):
217
227
  await task.update("working", f"Step {i}/10", progress=i/10)
218
-
219
228
  return "Done!"
220
229
  ```
221
230
 
222
- ### Level 7: Authentication
231
+ ### Level 7 Authentication
232
+
233
+ API keys are hashed in memory using SHA-256 — plaintext keys are never stored.
223
234
 
224
235
  ```python
225
236
  from a2a_lite import Agent, APIKeyAuth
@@ -231,8 +242,6 @@ agent = Agent(
231
242
  )
232
243
  ```
233
244
 
234
- API keys are hashed in memory using SHA-256 — plaintext keys are never stored.
235
-
236
245
  Other auth providers:
237
246
 
238
247
  ```python
@@ -261,7 +270,7 @@ async def whoami(auth: AuthResult) -> dict:
261
270
  return {"user": auth.identity, "scheme": auth.scheme}
262
271
  ```
263
272
 
264
- ### Level 8: CORS and Production Mode
273
+ ### Level 8 CORS & Production Mode
265
274
 
266
275
  ```python
267
276
  agent = Agent(
@@ -272,12 +281,24 @@ agent = Agent(
272
281
  )
273
282
  ```
274
283
 
275
- ### Level 9: Completion Hooks
284
+ ### Level 9 Lifecycle Hooks
276
285
 
277
286
  ```python
287
+ @agent.on_startup
288
+ async def startup():
289
+ print("Agent starting...")
290
+
291
+ @agent.on_shutdown
292
+ async def shutdown():
293
+ print("Agent stopping...")
294
+
278
295
  @agent.on_complete
279
296
  async def notify(skill_name, result, ctx):
280
297
  print(f"Skill {skill_name} completed with: {result}")
298
+
299
+ @agent.on_error
300
+ async def handle_error(error: Exception):
301
+ return {"error": str(error), "type": type(error).__name__}
281
302
  ```
282
303
 
283
304
  ---
@@ -286,7 +307,7 @@ async def notify(skill_name, result, ctx):
286
307
 
287
308
  ### AgentTestClient
288
309
 
289
- The synchronous test client for use with pytest:
310
+ Synchronous test client for pytest:
290
311
 
291
312
  ```python
292
313
  from a2a_lite import Agent, AgentTestClient
@@ -324,7 +345,7 @@ def test_list_skills():
324
345
 
325
346
  ### TestResult
326
347
 
327
- Every `client.call()` returns a `TestResult` with:
348
+ Every `client.call()` returns a `TestResult`:
328
349
 
329
350
  | Property | Description |
330
351
  |----------|-------------|
@@ -333,7 +354,7 @@ Every `client.call()` returns a `TestResult` with:
333
354
  | `.json()` | Parse text as JSON (raises on invalid JSON) |
334
355
  | `.raw_response` | Full A2A response dict |
335
356
 
336
- `TestResult` supports direct equality comparison for simple values (`result == 5`), but use `.data` for subscripting (`result.data["key"]`).
357
+ `TestResult` supports direct equality for simple values (`result == 5`), but use `.data` for subscripting (`result.data["key"]`).
337
358
 
338
359
  ### AsyncAgentTestClient
339
360
 
@@ -365,10 +386,11 @@ def test_streaming():
365
386
  ## CLI
366
387
 
367
388
  ```bash
368
- a2a-lite init my-agent # Create new project
369
- a2a-lite serve agent.py # Run agent from file
370
- a2a-lite inspect http://... # View agent capabilities
371
- a2a-lite test http://... skill # Test a skill
389
+ a2a-lite init my-agent # Scaffold a new project
390
+ a2a-lite serve agent.py # Run an agent from file
391
+ a2a-lite inspect http://... # View agent card & skills
392
+ a2a-lite test http://... skill # Smoke-test a skill
393
+ a2a-lite discover # Find agents on the local network (mDNS)
372
394
  a2a-lite version # Show version
373
395
  ```
374
396
 
@@ -427,7 +449,7 @@ Agent(
427
449
 
428
450
  ### Special Parameter Types
429
451
 
430
- These are auto-injected when detected in skill function signatures:
452
+ Auto-injected when detected in skill function signatures:
431
453
 
432
454
  | Type | Description |
433
455
  |------|-------------|
@@ -444,18 +466,22 @@ These are auto-injected when detected in skill function signatures:
444
466
  |---------|---------------|
445
467
  | [01_hello_world.py](examples/01_hello_world.py) | Simplest agent (8 lines) |
446
468
  | [02_calculator.py](examples/02_calculator.py) | Multiple skills |
469
+ | [03_async_agent.py](examples/03_async_agent.py) | Async operations & lifecycle hooks |
470
+ | [04_multi_agent/](examples/04_multi_agent) | Two agents communicating |
471
+ | [05_with_llm.py](examples/05_with_llm.py) | OpenAI / Anthropic integration |
447
472
  | [06_pydantic_models.py](examples/06_pydantic_models.py) | Auto Pydantic conversion |
473
+ | [07_middleware.py](examples/07_middleware.py) | Middleware pipeline |
448
474
  | [08_streaming.py](examples/08_streaming.py) | Streaming responses |
449
- | [09_testing.py](examples/09_testing.py) | Testing your agents |
450
- | [10_file_handling.py](examples/10_file_handling.py) | Handle files |
475
+ | [09_testing.py](examples/09_testing.py) | Built-in TestClient |
476
+ | [10_file_handling.py](examples/10_file_handling.py) | File upload & processing |
451
477
  | [11_task_tracking.py](examples/11_task_tracking.py) | Progress updates |
452
478
  | [12_with_auth.py](examples/12_with_auth.py) | Authentication |
453
479
 
454
480
  ---
455
481
 
456
- ## 100% A2A Protocol Compatible
482
+ ## A2A Protocol Mapping
457
483
 
458
- A2A Lite wraps the official A2A Python SDK. Every feature maps to real A2A protocol concepts:
484
+ Everything maps directly to the underlying protocol no magic, no lock-in.
459
485
 
460
486
  | A2A Lite | A2A Protocol |
461
487
  |----------|--------------|
@@ -464,6 +490,7 @@ A2A Lite wraps the official A2A Python SDK. Every feature maps to real A2A proto
464
490
  | `TaskContext.update()` | Task lifecycle states |
465
491
  | `FilePart` | A2A File parts |
466
492
  | `DataPart` | A2A Data parts |
493
+ | `Artifact` | A2A Artifacts |
467
494
  | `APIKeyAuth` / `BearerAuth` | Security schemes |
468
495
 
469
496
  ---
@@ -1,8 +1,11 @@
1
- # A2A Lite - Python
1
+ # A2A Lite Python
2
+
3
+ [![PyPI](https://img.shields.io/pypi/v/a2a-lite?label=PyPI&logo=pypi&logoColor=white)](https://pypi.org/project/a2a-lite/)
4
+ [![GitHub](https://img.shields.io/badge/GitHub-a2a--lite-blue?logo=github)](https://github.com/xvierd/a2a-lite)
2
5
 
3
6
  **Build A2A agents in 8 lines. Add features when you need them.**
4
7
 
5
- Wraps the official [A2A Python SDK](https://github.com/a2aproject/a2a-python) with a simple, intuitive API.
8
+ Wraps the official [A2A Python SDK](https://github.com/a2aproject/a2a-python) with a simple, decorator-based API. 100% protocol-compatible.
6
9
 
7
10
  ```python
8
11
  from a2a_lite import Agent
@@ -50,7 +53,7 @@ async def multiply(a: int, b: int) -> int:
50
53
  agent.run(port=8787)
51
54
  ```
52
55
 
53
- ### 2. Test it
56
+ ### 2. Test it (no HTTP needed)
54
57
 
55
58
  ```python
56
59
  from a2a_lite import Agent, AgentTestClient
@@ -66,7 +69,7 @@ result = client.call("add", a=2, b=3)
66
69
  assert result == 5
67
70
  ```
68
71
 
69
- ### 3. Call it
72
+ ### 3. Call it over the network
70
73
 
71
74
  ```bash
72
75
  curl -X POST http://localhost:8787/ \
@@ -89,7 +92,7 @@ curl -X POST http://localhost:8787/ \
89
92
 
90
93
  ## Progressive Complexity
91
94
 
92
- ### Level 1: Basic Skills
95
+ ### Level 1 Basic Skills
93
96
 
94
97
  ```python
95
98
  from a2a_lite import Agent
@@ -103,7 +106,7 @@ async def greet(name: str) -> str:
103
106
  agent.run()
104
107
  ```
105
108
 
106
- ### Level 2: Pydantic Models (Just Works)
109
+ ### Level 2 Pydantic Models
107
110
 
108
111
  Pass dicts from callers — they're auto-converted to Pydantic models:
109
112
 
@@ -129,7 +132,9 @@ async def count_users(users: List[User]) -> int:
129
132
  return len(users)
130
133
  ```
131
134
 
132
- ### Level 3: Streaming (Just Yield)
135
+ ### Level 3 Streaming
136
+
137
+ Just `yield` instead of `return`:
133
138
 
134
139
  ```python
135
140
  @agent.skill("chat", streaming=True)
@@ -138,7 +143,9 @@ async def chat(message: str):
138
143
  yield word + " "
139
144
  ```
140
145
 
141
- ### Level 4: Middleware
146
+ ### Level 4 Middleware
147
+
148
+ Cross-cutting concerns without touching skill code:
142
149
 
143
150
  ```python
144
151
  @agent.middleware
@@ -160,7 +167,9 @@ agent.add_middleware(rate_limit_middleware(max_per_minute=60))
160
167
  agent.add_middleware(retry_middleware(max_retries=3))
161
168
  ```
162
169
 
163
- ### Level 5: File Handling
170
+ ### Level 5 File Handling
171
+
172
+ Accept and return files through the A2A protocol:
164
173
 
165
174
  ```python
166
175
  from a2a_lite import FilePart
@@ -171,7 +180,9 @@ async def summarize(doc: FilePart) -> str:
171
180
  return f"Summary: {content[:100]}..."
172
181
  ```
173
182
 
174
- ### Level 6: Task Tracking
183
+ ### Level 6 Task Tracking
184
+
185
+ Long-running operations with progress updates:
175
186
 
176
187
  ```python
177
188
  from a2a_lite import TaskContext
@@ -181,14 +192,14 @@ agent = Agent(name="Bot", description="A bot", task_store="memory")
181
192
  @agent.skill("process")
182
193
  async def process(data: str, task: TaskContext) -> str:
183
194
  await task.update("working", "Starting...", progress=0.0)
184
-
185
195
  for i in range(10):
186
196
  await task.update("working", f"Step {i}/10", progress=i/10)
187
-
188
197
  return "Done!"
189
198
  ```
190
199
 
191
- ### Level 7: Authentication
200
+ ### Level 7 Authentication
201
+
202
+ API keys are hashed in memory using SHA-256 — plaintext keys are never stored.
192
203
 
193
204
  ```python
194
205
  from a2a_lite import Agent, APIKeyAuth
@@ -200,8 +211,6 @@ agent = Agent(
200
211
  )
201
212
  ```
202
213
 
203
- API keys are hashed in memory using SHA-256 — plaintext keys are never stored.
204
-
205
214
  Other auth providers:
206
215
 
207
216
  ```python
@@ -230,7 +239,7 @@ async def whoami(auth: AuthResult) -> dict:
230
239
  return {"user": auth.identity, "scheme": auth.scheme}
231
240
  ```
232
241
 
233
- ### Level 8: CORS and Production Mode
242
+ ### Level 8 CORS & Production Mode
234
243
 
235
244
  ```python
236
245
  agent = Agent(
@@ -241,12 +250,24 @@ agent = Agent(
241
250
  )
242
251
  ```
243
252
 
244
- ### Level 9: Completion Hooks
253
+ ### Level 9 Lifecycle Hooks
245
254
 
246
255
  ```python
256
+ @agent.on_startup
257
+ async def startup():
258
+ print("Agent starting...")
259
+
260
+ @agent.on_shutdown
261
+ async def shutdown():
262
+ print("Agent stopping...")
263
+
247
264
  @agent.on_complete
248
265
  async def notify(skill_name, result, ctx):
249
266
  print(f"Skill {skill_name} completed with: {result}")
267
+
268
+ @agent.on_error
269
+ async def handle_error(error: Exception):
270
+ return {"error": str(error), "type": type(error).__name__}
250
271
  ```
251
272
 
252
273
  ---
@@ -255,7 +276,7 @@ async def notify(skill_name, result, ctx):
255
276
 
256
277
  ### AgentTestClient
257
278
 
258
- The synchronous test client for use with pytest:
279
+ Synchronous test client for pytest:
259
280
 
260
281
  ```python
261
282
  from a2a_lite import Agent, AgentTestClient
@@ -293,7 +314,7 @@ def test_list_skills():
293
314
 
294
315
  ### TestResult
295
316
 
296
- Every `client.call()` returns a `TestResult` with:
317
+ Every `client.call()` returns a `TestResult`:
297
318
 
298
319
  | Property | Description |
299
320
  |----------|-------------|
@@ -302,7 +323,7 @@ Every `client.call()` returns a `TestResult` with:
302
323
  | `.json()` | Parse text as JSON (raises on invalid JSON) |
303
324
  | `.raw_response` | Full A2A response dict |
304
325
 
305
- `TestResult` supports direct equality comparison for simple values (`result == 5`), but use `.data` for subscripting (`result.data["key"]`).
326
+ `TestResult` supports direct equality for simple values (`result == 5`), but use `.data` for subscripting (`result.data["key"]`).
306
327
 
307
328
  ### AsyncAgentTestClient
308
329
 
@@ -334,10 +355,11 @@ def test_streaming():
334
355
  ## CLI
335
356
 
336
357
  ```bash
337
- a2a-lite init my-agent # Create new project
338
- a2a-lite serve agent.py # Run agent from file
339
- a2a-lite inspect http://... # View agent capabilities
340
- a2a-lite test http://... skill # Test a skill
358
+ a2a-lite init my-agent # Scaffold a new project
359
+ a2a-lite serve agent.py # Run an agent from file
360
+ a2a-lite inspect http://... # View agent card & skills
361
+ a2a-lite test http://... skill # Smoke-test a skill
362
+ a2a-lite discover # Find agents on the local network (mDNS)
341
363
  a2a-lite version # Show version
342
364
  ```
343
365
 
@@ -396,7 +418,7 @@ Agent(
396
418
 
397
419
  ### Special Parameter Types
398
420
 
399
- These are auto-injected when detected in skill function signatures:
421
+ Auto-injected when detected in skill function signatures:
400
422
 
401
423
  | Type | Description |
402
424
  |------|-------------|
@@ -413,18 +435,22 @@ These are auto-injected when detected in skill function signatures:
413
435
  |---------|---------------|
414
436
  | [01_hello_world.py](examples/01_hello_world.py) | Simplest agent (8 lines) |
415
437
  | [02_calculator.py](examples/02_calculator.py) | Multiple skills |
438
+ | [03_async_agent.py](examples/03_async_agent.py) | Async operations & lifecycle hooks |
439
+ | [04_multi_agent/](examples/04_multi_agent) | Two agents communicating |
440
+ | [05_with_llm.py](examples/05_with_llm.py) | OpenAI / Anthropic integration |
416
441
  | [06_pydantic_models.py](examples/06_pydantic_models.py) | Auto Pydantic conversion |
442
+ | [07_middleware.py](examples/07_middleware.py) | Middleware pipeline |
417
443
  | [08_streaming.py](examples/08_streaming.py) | Streaming responses |
418
- | [09_testing.py](examples/09_testing.py) | Testing your agents |
419
- | [10_file_handling.py](examples/10_file_handling.py) | Handle files |
444
+ | [09_testing.py](examples/09_testing.py) | Built-in TestClient |
445
+ | [10_file_handling.py](examples/10_file_handling.py) | File upload & processing |
420
446
  | [11_task_tracking.py](examples/11_task_tracking.py) | Progress updates |
421
447
  | [12_with_auth.py](examples/12_with_auth.py) | Authentication |
422
448
 
423
449
  ---
424
450
 
425
- ## 100% A2A Protocol Compatible
451
+ ## A2A Protocol Mapping
426
452
 
427
- A2A Lite wraps the official A2A Python SDK. Every feature maps to real A2A protocol concepts:
453
+ Everything maps directly to the underlying protocol no magic, no lock-in.
428
454
 
429
455
  | A2A Lite | A2A Protocol |
430
456
  |----------|--------------|
@@ -433,6 +459,7 @@ A2A Lite wraps the official A2A Python SDK. Every feature maps to real A2A proto
433
459
  | `TaskContext.update()` | Task lifecycle states |
434
460
  | `FilePart` | A2A File parts |
435
461
  | `DataPart` | A2A Data parts |
462
+ | `Artifact` | A2A Artifacts |
436
463
  | `APIKeyAuth` / `BearerAuth` | Security schemes |
437
464
 
438
465
  ---
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "a2a-lite"
3
- version = "0.2.4"
3
+ version = "0.2.5"
4
4
  description = "Simplified wrapper for Google's A2A Protocol SDK"
5
5
  readme = "README.md"
6
6
  license = "MIT"
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes