letta-client 0.1.77__py3-none-any.whl → 0.1.78__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of letta-client might be problematic. Click here for more details.
- letta_client/client.py +257 -1
- letta_client/core/client_wrapper.py +1 -1
- {letta_client-0.1.77.dist-info → letta_client-0.1.78.dist-info}/METADATA +1 -1
- {letta_client-0.1.77.dist-info → letta_client-0.1.78.dist-info}/RECORD +5 -5
- {letta_client-0.1.77.dist-info → letta_client-0.1.78.dist-info}/WHEEL +0 -0
letta_client/client.py
CHANGED
|
@@ -7,6 +7,7 @@ from abc import abstractmethod
|
|
|
7
7
|
from .base_client import AsyncLettaBase, LettaBase
|
|
8
8
|
from .core.request_options import RequestOptions
|
|
9
9
|
from .tools.client import ToolsClient as ToolsClientBase
|
|
10
|
+
from .tools.client import AsyncToolsClient as AsyncToolsClientBase
|
|
10
11
|
from .types.tool import Tool
|
|
11
12
|
|
|
12
13
|
# this is used as the default value for optional parameters
|
|
@@ -24,7 +25,7 @@ class AsyncLetta(AsyncLettaBase):
|
|
|
24
25
|
|
|
25
26
|
def __init__(self, *args, **kwargs):
|
|
26
27
|
super().__init__(*args, **kwargs)
|
|
27
|
-
self.tools =
|
|
28
|
+
self.tools = AsyncToolsClient(client_wrapper=self._client_wrapper)
|
|
28
29
|
|
|
29
30
|
|
|
30
31
|
class BaseTool(Tool):
|
|
@@ -380,3 +381,258 @@ class ToolsClient(ToolsClientBase):
|
|
|
380
381
|
return_char_limit=tool.return_char_limit or OMIT,
|
|
381
382
|
request_options=request_options,
|
|
382
383
|
)
|
|
384
|
+
|
|
385
|
+
|
|
386
|
+
class AsyncToolsClient(AsyncToolsClientBase):
|
|
387
|
+
|
|
388
|
+
async def create_from_function(
|
|
389
|
+
self,
|
|
390
|
+
*,
|
|
391
|
+
func: typing.Callable,
|
|
392
|
+
args_schema: typing.Optional[typing.Type[BaseModel]] = OMIT,
|
|
393
|
+
description: typing.Optional[str] = OMIT,
|
|
394
|
+
tags: typing.Optional[typing.Sequence[str]] = OMIT,
|
|
395
|
+
source_type: typing.Optional[str] = OMIT,
|
|
396
|
+
json_schema: typing.Optional[
|
|
397
|
+
typing.Dict[str, typing.Optional[typing.Any]]
|
|
398
|
+
] = OMIT,
|
|
399
|
+
return_char_limit: typing.Optional[int] = OMIT,
|
|
400
|
+
request_options: typing.Optional[RequestOptions] = None,
|
|
401
|
+
) -> Tool:
|
|
402
|
+
"""
|
|
403
|
+
Create a new tool from a callable
|
|
404
|
+
|
|
405
|
+
Parameters
|
|
406
|
+
----------
|
|
407
|
+
func : typing.Callable
|
|
408
|
+
The callable to create the tool from.
|
|
409
|
+
|
|
410
|
+
args_schema : typing.Optional[typing.Type[BaseModel]]
|
|
411
|
+
The arguments schema of the function, as a Pydantic model.
|
|
412
|
+
|
|
413
|
+
description : typing.Optional[str]
|
|
414
|
+
The description of the tool.
|
|
415
|
+
|
|
416
|
+
tags : typing.Optional[typing.Sequence[str]]
|
|
417
|
+
Metadata tags.
|
|
418
|
+
|
|
419
|
+
source_type : typing.Optional[str]
|
|
420
|
+
The source type of the function.
|
|
421
|
+
|
|
422
|
+
json_schema : typing.Optional[typing.Dict[str, typing.Optional[typing.Any]]]
|
|
423
|
+
The JSON schema of the function (auto-generated from source_code if not provided)
|
|
424
|
+
|
|
425
|
+
return_char_limit : typing.Optional[int]
|
|
426
|
+
The maximum number of characters in the response.
|
|
427
|
+
|
|
428
|
+
request_options : typing.Optional[RequestOptions]
|
|
429
|
+
Request-specific configuration.
|
|
430
|
+
|
|
431
|
+
Returns
|
|
432
|
+
-------
|
|
433
|
+
Tool
|
|
434
|
+
Successful Response
|
|
435
|
+
|
|
436
|
+
Examples
|
|
437
|
+
--------
|
|
438
|
+
from letta_client import Letta
|
|
439
|
+
|
|
440
|
+
client = Letta(
|
|
441
|
+
token="YOUR_TOKEN",
|
|
442
|
+
)
|
|
443
|
+
|
|
444
|
+
def add_two_numbers(a: int, b: int) -> int:
|
|
445
|
+
return a + b
|
|
446
|
+
|
|
447
|
+
await client.tools.create_from_function(
|
|
448
|
+
func=add_two_numbers,
|
|
449
|
+
)
|
|
450
|
+
|
|
451
|
+
class InventoryEntryData(BaseModel):
|
|
452
|
+
data: InventoryEntry
|
|
453
|
+
quantity_change: int
|
|
454
|
+
|
|
455
|
+
def manage_inventory(data: InventoryEntry, quantity_change: int) -> bool:
|
|
456
|
+
pass
|
|
457
|
+
|
|
458
|
+
await client.tools.create_from_function(
|
|
459
|
+
func=manage_inventory,
|
|
460
|
+
args_schema=InventoryEntryData,
|
|
461
|
+
)
|
|
462
|
+
"""
|
|
463
|
+
source_code = dedent(inspect.getsource(func))
|
|
464
|
+
args_json_schema = args_schema.model_json_schema() if args_schema and args_schema != OMIT else None
|
|
465
|
+
return await self.create(
|
|
466
|
+
source_code=source_code,
|
|
467
|
+
args_json_schema=args_json_schema,
|
|
468
|
+
description=description,
|
|
469
|
+
tags=tags,
|
|
470
|
+
source_type=source_type,
|
|
471
|
+
json_schema=json_schema,
|
|
472
|
+
return_char_limit=return_char_limit,
|
|
473
|
+
request_options=request_options,
|
|
474
|
+
)
|
|
475
|
+
|
|
476
|
+
|
|
477
|
+
async def upsert_from_function(
|
|
478
|
+
self,
|
|
479
|
+
*,
|
|
480
|
+
func: typing.Callable,
|
|
481
|
+
args_schema: typing.Optional[typing.Type[BaseModel]] = OMIT,
|
|
482
|
+
description: typing.Optional[str] = OMIT,
|
|
483
|
+
tags: typing.Optional[typing.Sequence[str]] = OMIT,
|
|
484
|
+
source_type: typing.Optional[str] = OMIT,
|
|
485
|
+
json_schema: typing.Optional[
|
|
486
|
+
typing.Dict[str, typing.Optional[typing.Any]]
|
|
487
|
+
] = OMIT,
|
|
488
|
+
return_char_limit: typing.Optional[int] = OMIT,
|
|
489
|
+
request_options: typing.Optional[RequestOptions] = None,
|
|
490
|
+
) -> Tool:
|
|
491
|
+
"""
|
|
492
|
+
Create or update a tool from a callable
|
|
493
|
+
|
|
494
|
+
Parameters
|
|
495
|
+
----------
|
|
496
|
+
func : typing.Callable
|
|
497
|
+
The callable to create or update the tool from.
|
|
498
|
+
|
|
499
|
+
args_schema : typing.Optional[typing.Type[BaseModel]]
|
|
500
|
+
The arguments schema of the function, as a Pydantic model.
|
|
501
|
+
|
|
502
|
+
description : typing.Optional[str]
|
|
503
|
+
The description of the tool.
|
|
504
|
+
|
|
505
|
+
tags : typing.Optional[typing.Sequence[str]]
|
|
506
|
+
Metadata tags.
|
|
507
|
+
|
|
508
|
+
source_type : typing.Optional[str]
|
|
509
|
+
The source type of the function.
|
|
510
|
+
|
|
511
|
+
json_schema : typing.Optional[typing.Dict[str, typing.Optional[typing.Any]]]
|
|
512
|
+
The JSON schema of the function (auto-generated from source_code if not provided)
|
|
513
|
+
|
|
514
|
+
return_char_limit : typing.Optional[int]
|
|
515
|
+
The maximum number of characters in the response.
|
|
516
|
+
|
|
517
|
+
request_options : typing.Optional[RequestOptions]
|
|
518
|
+
Request-specific configuration.
|
|
519
|
+
|
|
520
|
+
Returns
|
|
521
|
+
-------
|
|
522
|
+
Tool
|
|
523
|
+
Successful Response
|
|
524
|
+
|
|
525
|
+
Examples
|
|
526
|
+
--------
|
|
527
|
+
from letta_client import Letta
|
|
528
|
+
|
|
529
|
+
client = Letta(
|
|
530
|
+
token="YOUR_TOKEN",
|
|
531
|
+
)
|
|
532
|
+
|
|
533
|
+
def add_two_numbers(a: int, b: int) -> int:
|
|
534
|
+
return a + b
|
|
535
|
+
|
|
536
|
+
await client.tools.upsert_from_function(
|
|
537
|
+
func=add_two_numbers,
|
|
538
|
+
)
|
|
539
|
+
|
|
540
|
+
class InventoryEntryData(BaseModel):
|
|
541
|
+
data: InventoryEntry
|
|
542
|
+
quantity_change: int
|
|
543
|
+
|
|
544
|
+
def manage_inventory(data: InventoryEntry, quantity_change: int) -> bool:
|
|
545
|
+
pass
|
|
546
|
+
|
|
547
|
+
await client.tools.upsert_from_function(
|
|
548
|
+
func=manage_inventory,
|
|
549
|
+
args_schema=InventoryEntryData,
|
|
550
|
+
)
|
|
551
|
+
"""
|
|
552
|
+
source_code = dedent(inspect.getsource(func))
|
|
553
|
+
args_json_schema = args_schema.model_json_schema() if args_schema and args_schema != OMIT else None
|
|
554
|
+
return await self.upsert(
|
|
555
|
+
source_code=source_code,
|
|
556
|
+
args_json_schema=args_json_schema,
|
|
557
|
+
description=description,
|
|
558
|
+
tags=tags,
|
|
559
|
+
source_type=source_type,
|
|
560
|
+
json_schema=json_schema,
|
|
561
|
+
return_char_limit=return_char_limit,
|
|
562
|
+
request_options=request_options,
|
|
563
|
+
)
|
|
564
|
+
|
|
565
|
+
async def add(
|
|
566
|
+
self,
|
|
567
|
+
*,
|
|
568
|
+
tool: BaseTool,
|
|
569
|
+
request_options: typing.Optional[RequestOptions] = None,
|
|
570
|
+
) -> Tool:
|
|
571
|
+
"""
|
|
572
|
+
Add a tool to Letta from a custom Tool class
|
|
573
|
+
|
|
574
|
+
Parameters
|
|
575
|
+
----------
|
|
576
|
+
tool : BaseTool
|
|
577
|
+
The tool object to be added.
|
|
578
|
+
|
|
579
|
+
request_options : typing.Optional[RequestOptions]
|
|
580
|
+
Request-specific configuration.
|
|
581
|
+
|
|
582
|
+
Returns
|
|
583
|
+
-------
|
|
584
|
+
Tool
|
|
585
|
+
Successful Response
|
|
586
|
+
|
|
587
|
+
Examples
|
|
588
|
+
--------
|
|
589
|
+
from letta_client import Letta
|
|
590
|
+
|
|
591
|
+
client = Letta(
|
|
592
|
+
token="YOUR_TOKEN",
|
|
593
|
+
)
|
|
594
|
+
|
|
595
|
+
class InventoryItem(BaseModel):
|
|
596
|
+
sku: str # Unique product identifier
|
|
597
|
+
name: str # Product name
|
|
598
|
+
price: float # Current price
|
|
599
|
+
category: str # Product category (e.g., "Electronics", "Clothing")
|
|
600
|
+
|
|
601
|
+
class InventoryEntry(BaseModel):
|
|
602
|
+
timestamp: int # Unix timestamp of the transaction
|
|
603
|
+
item: InventoryItem # The product being updated
|
|
604
|
+
transaction_id: str # Unique identifier for this inventory update
|
|
605
|
+
|
|
606
|
+
class InventoryEntryData(BaseModel):
|
|
607
|
+
data: InventoryEntry
|
|
608
|
+
quantity_change: int # Change in quantity (positive for additions, negative for removals)
|
|
609
|
+
|
|
610
|
+
class ManageInventoryTool(BaseTool):
|
|
611
|
+
name: str = "manage_inventory"
|
|
612
|
+
args_schema: Type[BaseModel] = InventoryEntryData
|
|
613
|
+
description: str = "Update inventory catalogue with a new data entry"
|
|
614
|
+
tags: List[str] = ["inventory", "shop"]
|
|
615
|
+
|
|
616
|
+
def run(self, data: InventoryEntry, quantity_change: int) -> bool:
|
|
617
|
+
'''
|
|
618
|
+
Implementation of the manage_inventory tool
|
|
619
|
+
'''
|
|
620
|
+
print(f"Updated inventory for {data.item.name} with a quantity change of {quantity_change}")
|
|
621
|
+
return True
|
|
622
|
+
|
|
623
|
+
await client.tools.add(
|
|
624
|
+
tool=ManageInventoryTool()
|
|
625
|
+
)
|
|
626
|
+
"""
|
|
627
|
+
source_code = tool.get_source_code()
|
|
628
|
+
args_json_schema = tool.args_schema.model_json_schema() if tool.args_schema else None
|
|
629
|
+
return await self.upsert(
|
|
630
|
+
source_code=source_code,
|
|
631
|
+
args_json_schema=args_json_schema or OMIT,
|
|
632
|
+
description=tool.description or OMIT,
|
|
633
|
+
tags=tool.tags or OMIT,
|
|
634
|
+
source_type=tool.source_type or OMIT,
|
|
635
|
+
json_schema=tool.json_schema or OMIT,
|
|
636
|
+
return_char_limit=tool.return_char_limit or OMIT,
|
|
637
|
+
request_options=request_options,
|
|
638
|
+
)
|
|
@@ -16,7 +16,7 @@ class BaseClientWrapper:
|
|
|
16
16
|
headers: typing.Dict[str, str] = {
|
|
17
17
|
"X-Fern-Language": "Python",
|
|
18
18
|
"X-Fern-SDK-Name": "letta-client",
|
|
19
|
-
"X-Fern-SDK-Version": "0.1.
|
|
19
|
+
"X-Fern-SDK-Version": "0.1.78",
|
|
20
20
|
}
|
|
21
21
|
if self.token is not None:
|
|
22
22
|
headers["Authorization"] = f"Bearer {self.token}"
|
|
@@ -231,10 +231,10 @@ letta_client/agents/types/update_agent_tool_rules_item.py,sha256=O0W83nOK8oMx_6N
|
|
|
231
231
|
letta_client/base_client.py,sha256=bF1nEcPGrhNqelaWz3DgROYdroGsBFCjpAHHri0uq7I,8629
|
|
232
232
|
letta_client/blocks/__init__.py,sha256=FTtvy8EDg9nNNg9WCatVgKTRYV8-_v1roeGPAKoa_pw,65
|
|
233
233
|
letta_client/blocks/client.py,sha256=LE9dsHaBxFLC3G035f0VpNDG7XKWRK8y9OXpeFCMvUw,30082
|
|
234
|
-
letta_client/client.py,sha256=
|
|
234
|
+
letta_client/client.py,sha256=k2mZqqEWciVmEQHgipjCK4kQILk74hpSqzcdNwdql9A,21212
|
|
235
235
|
letta_client/core/__init__.py,sha256=OKbX2aCZXgHCDUsCouqv-OiX32xA6eFFCKIUH9M5Vzk,1591
|
|
236
236
|
letta_client/core/api_error.py,sha256=RE8LELok2QCjABadECTvtDp7qejA1VmINCh6TbqPwSE,426
|
|
237
|
-
letta_client/core/client_wrapper.py,sha256=
|
|
237
|
+
letta_client/core/client_wrapper.py,sha256=JO6fN9Yvpg2o0vMf-HNqjk5yv0wFGsDDnc-w-Rm8MhQ,1997
|
|
238
238
|
letta_client/core/datetime_utils.py,sha256=nBys2IsYrhPdszxGKCNRPSOCwa-5DWOHG95FB8G9PKo,1047
|
|
239
239
|
letta_client/core/file.py,sha256=d4NNbX8XvXP32z8KpK2Xovv33nFfruIrpz0QWxlgpZk,2663
|
|
240
240
|
letta_client/core/http_client.py,sha256=Z77OIxIbL4OAB2IDqjRq_sYa5yNYAWfmdhdCSSvh6Y4,19552
|
|
@@ -689,6 +689,6 @@ letta_client/voice/__init__.py,sha256=ZrZEuXIukVGhsfM-i0dIFfqjeSOBMPeEgDva7Vvnip
|
|
|
689
689
|
letta_client/voice/client.py,sha256=2KKJiteGk5HQM79ne1jOPl_ZyUTfZM_gXNdZZ_ndPU8,6485
|
|
690
690
|
letta_client/voice/types/__init__.py,sha256=hBLJcrom99DkDxxsVRU2ni8kPx6SsCy8gtAJvNOz26w,199
|
|
691
691
|
letta_client/voice/types/create_voice_chat_completions_request.py,sha256=K4__83rXRCshfdobyAmH-5fUDJQ_PeSQetTUeC4Abk0,381
|
|
692
|
-
letta_client-0.1.
|
|
693
|
-
letta_client-0.1.
|
|
694
|
-
letta_client-0.1.
|
|
692
|
+
letta_client-0.1.78.dist-info/METADATA,sha256=VxRfLmu98Hu1fY_4Gju0oKLYXZUvVp88drgfAQaV78E,5041
|
|
693
|
+
letta_client-0.1.78.dist-info/WHEEL,sha256=Zb28QaM1gQi8f4VCBhsUklF61CTlNYfs9YAZn-TOGFk,88
|
|
694
|
+
letta_client-0.1.78.dist-info/RECORD,,
|
|
File without changes
|