intentkit 0.7.5.dev16__py3-none-any.whl → 0.7.5.dev18__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 intentkit might be problematic. Click here for more details.

@@ -4,23 +4,13 @@ import httpx
4
4
  from langchain.tools.base import ToolException
5
5
  from pydantic import BaseModel, Field
6
6
 
7
- from .base import EnsoBaseTool, base_url, default_chain_id
7
+ from .base import EnsoBaseTool, base_url
8
8
 
9
9
 
10
10
  class EnsoGetBalancesInput(BaseModel):
11
- """
12
- Input model for retrieving wallet balances.
13
- """
11
+ """Input model for retrieving wallet balances."""
14
12
 
15
- chainId: int = Field(
16
- default_chain_id, description="Chain ID of the blockchain network"
17
- )
18
- # eoaAddress: str = Field(
19
- # description="Address of the eoa with which to associate the ensoWallet for balances"
20
- # )
21
- # useEoa: bool = Field(
22
- # description="If true returns balances for the provided eoaAddress, instead of the associated ensoWallet"
23
- # )
13
+ chainId: int | None = Field(None, description="Chain ID of the blockchain network")
24
14
 
25
15
 
26
16
  class WalletBalance(BaseModel):
@@ -31,9 +21,7 @@ class WalletBalance(BaseModel):
31
21
 
32
22
 
33
23
  class EnsoGetBalancesOutput(BaseModel):
34
- """
35
- Output model for retrieving wallet balances.
36
- """
24
+ """Output model for retrieving wallet balances."""
37
25
 
38
26
  res: list[WalletBalance] | None = Field(
39
27
  None, description="The wallet's balances along with token details."
@@ -41,15 +29,7 @@ class EnsoGetBalancesOutput(BaseModel):
41
29
 
42
30
 
43
31
  class EnsoGetWalletBalances(EnsoBaseTool):
44
- """
45
- This tool allows querying for first 20 token balances of a specific wallet
46
- and blockchain network.
47
-
48
- Attributes:
49
- name (str): Name of the tool, specifically "enso_get_wallet_balances".
50
- description (str): Comprehensive description of the tool's purpose and functionality.
51
- args_schema (Type[BaseModel]): Schema for input arguments, specifying expected parameters.
52
- """
32
+ """Retrieve token balances of a wallet on a specified blockchain network."""
53
33
 
54
34
  name: str = "enso_get_wallet_balances"
55
35
  description: str = (
@@ -59,61 +39,48 @@ class EnsoGetWalletBalances(EnsoBaseTool):
59
39
 
60
40
  async def _arun(
61
41
  self,
62
- chainId: int = default_chain_id,
63
- **kwargs,
42
+ chainId: int | None = None,
43
+ **_: object,
64
44
  ) -> EnsoGetBalancesOutput:
65
- """
66
- Run the tool to get token balances of a wallet.
67
-
68
- Args:
69
- chainId (int): Chain ID of the blockchain network.
70
-
71
- Returns:
72
- EnsoGetBalancesOutput: The list of balances or an error message.
73
- """
74
- url = f"{base_url}/api/v1/wallet/balances"
75
-
76
45
  context = self.get_context()
46
+ resolved_chain_id = self.resolve_chain_id(context, chainId)
77
47
  api_token = self.get_api_token(context)
78
- account = await self.get_account(context)
48
+ wallet_address = await self.get_wallet_address(context)
49
+
79
50
  headers = {
80
51
  "accept": "application/json",
81
52
  "Authorization": f"Bearer {api_token}",
82
53
  }
83
54
 
84
- params = EnsoGetBalancesInput(chainId=chainId).model_dump(exclude_none=True)
85
- params["eoaAddress"] = account.address
55
+ params = EnsoGetBalancesInput(chainId=resolved_chain_id).model_dump(
56
+ exclude_none=True
57
+ )
58
+ params["eoaAddress"] = wallet_address
86
59
  params["useEoa"] = True
87
60
 
88
61
  async with httpx.AsyncClient() as client:
89
62
  try:
90
- # Send the GET request
91
- response = await client.get(url, headers=headers, params=params)
63
+ response = await client.get(
64
+ f"{base_url}/api/v1/wallet/balances",
65
+ headers=headers,
66
+ params=params,
67
+ )
92
68
  response.raise_for_status()
93
-
94
- # Map the response JSON into the WalletBalance model
95
69
  json_dict = response.json()[:20]
96
70
  res = [WalletBalance(**item) for item in json_dict]
97
-
98
- # Return the parsed response
99
71
  return EnsoGetBalancesOutput(res=res)
100
72
  except httpx.RequestError as req_err:
101
73
  raise ToolException("request error from Enso API") from req_err
102
74
  except httpx.HTTPStatusError as http_err:
103
75
  raise ToolException("http error from Enso API") from http_err
104
- except Exception as e:
105
- raise ToolException(f"error from Enso API: {e}") from e
76
+ except Exception as exc: # pragma: no cover - defensive
77
+ raise ToolException(f"error from Enso API: {exc}") from exc
106
78
 
107
79
 
108
80
  class EnsoGetApprovalsInput(BaseModel):
109
- """
110
- Input model for retrieving wallet approvals.
111
- """
81
+ """Input model for retrieving wallet approvals."""
112
82
 
113
- chainId: int = Field(
114
- default_chain_id, description="Chain ID of the blockchain network"
115
- )
116
- fromAddress: str = Field(description="Address of the wallet")
83
+ chainId: int | None = Field(None, description="Chain ID of the blockchain network")
117
84
  routingStrategy: Literal["ensowallet", "router", "delegate"] | None = Field(
118
85
  None, description="Routing strategy to use"
119
86
  )
@@ -126,9 +93,7 @@ class WalletAllowance(BaseModel):
126
93
 
127
94
 
128
95
  class EnsoGetApprovalsOutput(BaseModel):
129
- """
130
- Output model for retrieving wallet approvals.
131
- """
96
+ """Output model for retrieving wallet approvals."""
132
97
 
133
98
  res: list[WalletAllowance] | None = Field(
134
99
  None, description="Response containing the list of token approvals."
@@ -136,42 +101,24 @@ class EnsoGetApprovalsOutput(BaseModel):
136
101
 
137
102
 
138
103
  class EnsoGetWalletApprovals(EnsoBaseTool):
139
- """
140
- This tool allows querying for first 50 token spend approvals associated with a specific wallet
141
- and blockchain network.
142
-
143
- Attributes:
144
- name (str): Name of the tool, specifically "enso_get_wallet_approvals".
145
- description (str): Comprehensive description of the tool's purpose and functionality.
146
- args_schema (Type[BaseModel]): Schema for input arguments, specifying expected parameters.
147
- """
104
+ """Retrieve token spend approvals for a wallet on a specified blockchain network."""
148
105
 
149
106
  name: str = "enso_get_wallet_approvals"
150
107
  description: str = (
151
108
  "Retrieve token spend approvals for a wallet on a specified blockchain network."
152
109
  )
153
- args_schema: Type[BaseModel] = EnsoGetApprovalsOutput
110
+ args_schema: Type[BaseModel] = EnsoGetApprovalsInput
154
111
 
155
112
  async def _arun(
156
113
  self,
157
- chainId: int = default_chain_id,
158
- **kwargs,
114
+ chainId: int | None = None,
115
+ routingStrategy: Literal["ensowallet", "router", "delegate"] | None = None,
116
+ **_: object,
159
117
  ) -> EnsoGetApprovalsOutput:
160
- """
161
- Run the tool to get token approvals for a wallet.
162
-
163
- Args:
164
- chainId (int): Chain ID of the blockchain network.
165
- **kwargs: optional kwargs for the tool with args schema defined in EnsoGetApprovalsInput.
166
-
167
- Returns:
168
- EnsoGetApprovalsOutput: The list of approvals or an error message.
169
- """
170
- url = f"{base_url}/api/v1/wallet/approvals"
171
-
172
118
  context = self.get_context()
119
+ resolved_chain_id = self.resolve_chain_id(context, chainId)
173
120
  api_token = self.get_api_token(context)
174
- account = await self.get_account(context)
121
+ wallet_address = await self.get_wallet_address(context)
175
122
 
176
123
  headers = {
177
124
  "accept": "application/json",
@@ -179,26 +126,21 @@ class EnsoGetWalletApprovals(EnsoBaseTool):
179
126
  }
180
127
 
181
128
  params = EnsoGetApprovalsInput(
182
- chainId=chainId,
183
- fromAddress=account.address,
184
- )
185
-
186
- if kwargs.get("routingStrategy"):
187
- params.routingStrategy = kwargs["routingStrategy"]
129
+ chainId=resolved_chain_id,
130
+ routingStrategy=routingStrategy,
131
+ ).model_dump(exclude_none=True)
132
+ params["fromAddress"] = wallet_address
188
133
 
189
134
  async with httpx.AsyncClient() as client:
190
135
  try:
191
- # Send the GET request
192
136
  response = await client.get(
193
- url, headers=headers, params=params.model_dump(exclude_none=True)
137
+ f"{base_url}/api/v1/wallet/approvals",
138
+ headers=headers,
139
+ params=params,
194
140
  )
195
141
  response.raise_for_status()
196
-
197
- # Map the response JSON into the ApprovalsResponse model
198
142
  json_dict = response.json()[:50]
199
143
  res = [WalletAllowance(**item) for item in json_dict]
200
-
201
- # Return the parsed response
202
144
  return EnsoGetApprovalsOutput(res=res)
203
145
  except httpx.RequestError as req_err:
204
146
  raise ToolException(
@@ -208,29 +150,23 @@ class EnsoGetWalletApprovals(EnsoBaseTool):
208
150
  raise ToolException(
209
151
  f"http error from Enso API: {http_err}"
210
152
  ) from http_err
211
- except Exception as e:
212
- raise ToolException(f"error from Enso API: {e}") from e
153
+ except Exception as exc: # pragma: no cover - defensive
154
+ raise ToolException(f"error from Enso API: {exc}") from exc
213
155
 
214
156
 
215
157
  class EnsoWalletApproveInput(BaseModel):
216
- """
217
- Input model for approve the wallet.
218
- """
158
+ """Input model for approving token spend for the wallet."""
219
159
 
220
160
  tokenAddress: str = Field(description="ERC20 token address of the token to approve")
221
161
  amount: int = Field(description="Amount of tokens to approve in wei")
222
- chainId: int = Field(
223
- default_chain_id, description="Chain ID of the blockchain network"
224
- )
162
+ chainId: int | None = Field(None, description="Chain ID of the blockchain network")
225
163
  routingStrategy: Literal["ensowallet", "router", "delegate"] | None = Field(
226
164
  None, description="Routing strategy to use"
227
165
  )
228
166
 
229
167
 
230
168
  class EnsoWalletApproveOutput(BaseModel):
231
- """
232
- Output model for approve token for the wallet.
233
- """
169
+ """Output model for approve token for the wallet."""
234
170
 
235
171
  gas: str | None = Field(None, description="The gas estimate for the transaction")
236
172
  token: str | None = Field(None, description="The token address to approve")
@@ -239,133 +175,82 @@ class EnsoWalletApproveOutput(BaseModel):
239
175
 
240
176
 
241
177
  class EnsoWalletApproveArtifact(BaseModel):
242
- """
243
- Output model for approve token for the wallet.
244
- """
178
+ """Artifact returned after broadcasting an approval transaction."""
245
179
 
246
- tx: object | None = Field(None, description="The tx object to use in `ethers`")
180
+ tx: object | None = Field(
181
+ None, description="The transaction object to use in `ethers`"
182
+ )
247
183
  txHash: str | None = Field(None, description="The transaction hash")
248
184
 
249
185
 
250
186
  class EnsoWalletApprove(EnsoBaseTool):
251
- """
252
- This tool is used specifically for broadcasting a ERC20 token spending approval transaction to the network.
253
- It should only be used when the user explicitly requests to broadcast an approval transaction with a specific amount for a certain token.
254
-
255
- **Example Usage:**
256
-
257
- "Broadcast an approval transaction for 10 USDC to the wallet."
258
-
259
- **Important:**
260
- - This tool should be used with extreme caution.
261
- - Approving token spending grants another account permission to spend your tokens.
262
-
263
- Attributes:
264
- name (str): Name of the tool, specifically "enso_wallet_approve".
265
- description (str): Comprehensive description of the tool's purpose and functionality.
266
- args_schema (Type[BaseModel]): Schema for input arguments, specifying expected parameters.
267
- """
187
+ """Broadcast an ERC20 token spending approval transaction."""
268
188
 
269
189
  name: str = "enso_wallet_approve"
270
- description: str = "This tool is used specifically for broadcasting a ERC20 token spending approval transaction to the network. It should only be used when the user explicitly requests to broadcast an approval transaction with a specific amount for a certain token."
190
+ description: str = (
191
+ "This tool is used specifically for broadcasting a ERC20 token spending approval transaction to the "
192
+ "network. It should only be used when the user explicitly requests to broadcast an approval transaction "
193
+ "with a specific amount for a certain token."
194
+ )
271
195
  args_schema: Type[BaseModel] = EnsoWalletApproveInput
272
196
  response_format: str = "content_and_artifact"
273
197
 
274
- # def _run(
275
- # self,
276
- # tokenAddress: str,
277
- # amount: int,
278
- # chainId: int = default_chain_id,
279
- # **kwargs,
280
- # ) -> Tuple[EnsoBroadcastWalletApproveOutput, EnsoBroadcastWalletApproveArtifact]:
281
- # """Run the tool to approve enso router for a wallet.
282
-
283
- # Returns:
284
- # Tuple[EnsoBroadcastWalletApproveOutput, EnsoBroadcastWalletApproveArtifact]: A structured output containing the result of token approval.
285
-
286
- # Raises:
287
- # Exception: If there's an error accessing the Enso API.
288
- # """
289
- # raise NotImplementedError("Use _arun instead")
290
-
291
198
  async def _arun(
292
199
  self,
293
200
  tokenAddress: str,
294
201
  amount: int,
295
- chainId: int = default_chain_id,
296
- **kwargs,
202
+ chainId: int | None = None,
203
+ routingStrategy: Literal["ensowallet", "router", "delegate"] | None = None,
204
+ **_: object,
297
205
  ) -> Tuple[EnsoWalletApproveOutput, EnsoWalletApproveArtifact]:
298
- """
299
- Run the tool to approve enso router for a wallet.
300
-
301
- Args:
302
- tokenAddress (str): ERC20 token address of the token to approve.
303
- amount (int): Amount of tokens to approve in wei.
304
- chainId (int): Chain ID of the blockchain network.
305
- **kwargs: optional kwargs for the tool with args schema defined in EnsoGetApproveInput.
306
-
307
- Returns:
308
- Tuple[EnsoBroadcastWalletApproveOutput, EnsoBroadcastWalletApproveArtifact]: The list of approve transaction output or an error message.
309
- """
310
- url = f"{base_url}/api/v1/wallet/approve"
311
206
  context = self.get_context()
207
+ resolved_chain_id = self.resolve_chain_id(context, chainId)
312
208
  api_token = self.get_api_token(context)
313
- account = await self.get_account(context)
209
+ wallet_address = await self.get_wallet_address(context)
314
210
 
315
211
  headers = {
316
212
  "accept": "application/json",
317
213
  "Authorization": f"Bearer {api_token}",
318
214
  }
319
215
 
320
- from_address = account.address
321
-
322
216
  params = EnsoWalletApproveInput(
323
217
  tokenAddress=tokenAddress,
324
218
  amount=amount,
325
- chainId=chainId,
326
- )
327
-
328
- if kwargs.get("routingStrategy"):
329
- params.routingStrategy = kwargs["routingStrategy"]
330
-
331
- params = params.model_dump(exclude_none=True)
219
+ chainId=resolved_chain_id,
220
+ routingStrategy=routingStrategy,
221
+ ).model_dump(exclude_none=True)
222
+ params["fromAddress"] = wallet_address
332
223
 
333
- params["fromAddress"] = from_address
334
-
335
- with httpx.Client() as client:
224
+ async with httpx.AsyncClient() as client:
336
225
  try:
337
- # Send the GET request
338
- response = client.get(url, headers=headers, params=params)
226
+ response = await client.get(
227
+ f"{base_url}/api/v1/wallet/approve",
228
+ headers=headers,
229
+ params=params,
230
+ )
339
231
  response.raise_for_status()
340
232
 
341
- # Map the response JSON into the WalletApproveTransaction model
342
233
  json_dict = response.json()
343
234
  content = EnsoWalletApproveOutput(**json_dict)
344
235
  artifact = EnsoWalletApproveArtifact(**json_dict)
345
236
 
346
- # Use the wallet provider to send the transaction
347
237
  wallet_provider = await self.get_wallet_provider(context)
348
-
349
- # Extract transaction data from the Enso API response
350
238
  tx_data = json_dict.get("tx", {})
351
239
  if tx_data:
352
- # Send the transaction using the wallet provider
353
240
  tx_hash = wallet_provider.send_transaction(
354
241
  {
355
242
  "to": tx_data.get("to"),
356
243
  "data": tx_data.get("data", "0x"),
357
244
  "value": tx_data.get("value", 0),
245
+ "from": wallet_address,
358
246
  }
359
247
  )
360
248
 
361
- # Wait for transaction confirmation
362
249
  wallet_provider.wait_for_transaction_receipt(tx_hash)
363
250
  artifact.txHash = tx_hash
364
251
  else:
365
- # For now, return without executing the transaction if no tx data
366
252
  artifact.txHash = "0x0000000000000000000000000000000000000000000000000000000000000000"
367
253
 
368
- # Return the parsed response
369
254
  return (content, artifact)
370
255
  except httpx.RequestError as req_err:
371
256
  raise ToolException(
@@ -375,5 +260,5 @@ class EnsoWalletApprove(EnsoBaseTool):
375
260
  raise ToolException(
376
261
  f"http error from Enso API: {http_err}"
377
262
  ) from http_err
378
- except Exception as e:
379
- raise ToolException(f"error from Enso API: {e}") from e
263
+ except Exception as exc: # pragma: no cover - defensive
264
+ raise ToolException(f"error from Enso API: {exc}") from exc
@@ -1,5 +1,5 @@
1
1
  import logging
2
- from typing import List, Optional, TypedDict
2
+ from typing import Any, List, Optional, TypedDict
3
3
 
4
4
  from intentkit.abstracts.skill import SkillStoreABC
5
5
  from intentkit.skills.base import SkillConfig, SkillState
@@ -32,10 +32,10 @@ async def get_skills(
32
32
  config: "Config",
33
33
  is_private: bool,
34
34
  store: SkillStoreABC,
35
- **_,
35
+ **_: Any,
36
36
  ) -> list[LiFiBaseTool]:
37
37
  """Get all LiFi skills."""
38
- available_skills = []
38
+ available_skills: list[str] = []
39
39
 
40
40
  # Log configuration
41
41
  logger.info(f"[LiFi_Skills] Initializing with config: {config}")
@@ -57,7 +57,7 @@ async def get_skills(
57
57
  logger.info(f"[LiFi_Skills] Available skills: {available_skills}")
58
58
 
59
59
  # Get each skill using the cached getter
60
- skills = []
60
+ skills: list[LiFiBaseTool] = []
61
61
  for name in available_skills:
62
62
  try:
63
63
  skill = get_lifi_skill(name, store, config)
@@ -2,11 +2,12 @@ import asyncio
2
2
  from typing import Any, Dict, List, Optional, Type
3
3
 
4
4
  import httpx
5
+ from coinbase_agentkit import CdpEvmWalletProvider
5
6
  from pydantic import BaseModel, Field
6
7
  from web3 import Web3
7
8
 
8
9
  from intentkit.abstracts.skill import SkillStoreABC
9
- from intentkit.clients import get_cdp_client
10
+ from intentkit.clients import CdpClient, get_cdp_client
10
11
  from intentkit.skills.lifi.base import LiFiBaseTool
11
12
  from intentkit.skills.lifi.token_quote import TokenQuote
12
13
  from intentkit.skills.lifi.utils import (
@@ -69,7 +70,7 @@ class TokenExecute(LiFiBaseTool):
69
70
  default_slippage: float = 0.03
70
71
  allowed_chains: Optional[List[str]] = None
71
72
  max_execution_time: int = 300
72
- quote_tool: TokenQuote = Field(default=None, exclude=True)
73
+ quote_tool: Optional[TokenQuote] = Field(default=None, exclude=True)
73
74
 
74
75
  def __init__(
75
76
  self,
@@ -77,7 +78,7 @@ class TokenExecute(LiFiBaseTool):
77
78
  default_slippage: float = 0.03,
78
79
  allowed_chains: Optional[List[str]] = None,
79
80
  max_execution_time: int = 300,
80
- ):
81
+ ) -> None:
81
82
  """Initialize the TokenExecute skill with configuration options."""
82
83
  super().__init__(skill_store=skill_store)
83
84
  self.default_slippage = default_slippage
@@ -93,6 +94,8 @@ class TokenExecute(LiFiBaseTool):
93
94
 
94
95
  def _format_quote_result(self, data: Dict[str, Any]) -> str:
95
96
  """Format the quote result in a readable format."""
97
+ if self.quote_tool is None:
98
+ raise RuntimeError("Quote tool is not initialized")
96
99
  # Use the same formatting as token_quote
97
100
  return self.quote_tool._format_quote_result(data)
98
101
 
@@ -103,7 +106,7 @@ class TokenExecute(LiFiBaseTool):
103
106
  from_token: str,
104
107
  to_token: str,
105
108
  from_amount: str,
106
- slippage: float = None,
109
+ slippage: Optional[float] = None,
107
110
  **kwargs,
108
111
  ) -> str:
109
112
  """Execute a token transfer."""
@@ -168,7 +171,9 @@ class TokenExecute(LiFiBaseTool):
168
171
 
169
172
  # Step 3: Execute transaction
170
173
  tx_hash = await self._execute_transfer_transaction(
171
- cdp_wallet_provider, quote_data
174
+ cdp_wallet_provider,
175
+ quote_data,
176
+ from_address,
172
177
  )
173
178
 
174
179
  # Step 4: Monitor status and return result
@@ -180,10 +185,12 @@ class TokenExecute(LiFiBaseTool):
180
185
  self.logger.error("LiFi_Error: %s", str(e))
181
186
  return f"An unexpected error occurred: {str(e)}"
182
187
 
183
- async def _get_cdp_wallet_provider(self, agent_id: str):
188
+ async def _get_cdp_wallet_provider(
189
+ self, agent_id: str
190
+ ) -> CdpEvmWalletProvider | str:
184
191
  """Get CDP wallet provider with error handling."""
185
192
  try:
186
- cdp_client = await get_cdp_client(agent_id, self.skill_store)
193
+ cdp_client: CdpClient = await get_cdp_client(agent_id, self.skill_store)
187
194
  if not cdp_client:
188
195
  return "CDP client not available. Please ensure your agent has CDP wallet configuration."
189
196
 
@@ -207,7 +214,7 @@ class TokenExecute(LiFiBaseTool):
207
214
  from_amount: str,
208
215
  slippage: float,
209
216
  from_address: str,
210
- ) -> Dict[str, Any]:
217
+ ) -> Dict[str, Any] | str:
211
218
  """Get quote from LiFi API."""
212
219
  api_params = build_quote_params(
213
220
  from_chain,
@@ -249,7 +256,7 @@ class TokenExecute(LiFiBaseTool):
249
256
  return data
250
257
 
251
258
  async def _handle_token_approval(
252
- self, wallet_provider, quote_data: Dict[str, Any]
259
+ self, wallet_provider: CdpEvmWalletProvider, quote_data: Dict[str, Any]
253
260
  ) -> Optional[str]:
254
261
  """Handle ERC20 token approval if needed."""
255
262
  estimate = quote_data.get("estimate", {})
@@ -273,13 +280,18 @@ class TokenExecute(LiFiBaseTool):
273
280
  raise Exception(f"Failed to approve token: {str(e)}")
274
281
 
275
282
  async def _execute_transfer_transaction(
276
- self, wallet_provider, quote_data: Dict[str, Any]
283
+ self,
284
+ wallet_provider: CdpEvmWalletProvider,
285
+ quote_data: Dict[str, Any],
286
+ from_address: str,
277
287
  ) -> str:
278
288
  """Execute the main transfer transaction."""
279
289
  transaction_request = quote_data.get("transactionRequest")
280
290
 
281
291
  try:
282
- tx_params = prepare_transaction_params(transaction_request)
292
+ tx_params = prepare_transaction_params(
293
+ transaction_request, wallet_address=from_address
294
+ )
283
295
  self.logger.info(
284
296
  f"Sending transaction to {tx_params['to']} with value {tx_params['value']}"
285
297
  )
@@ -407,7 +419,7 @@ class TokenExecute(LiFiBaseTool):
407
419
 
408
420
  async def _check_and_set_allowance(
409
421
  self,
410
- wallet_provider,
422
+ wallet_provider: CdpEvmWalletProvider,
411
423
  token_address: str,
412
424
  approval_address: str,
413
425
  amount: str,
@@ -65,7 +65,7 @@ class TokenQuote(LiFiBaseTool):
65
65
  skill_store: SkillStoreABC,
66
66
  default_slippage: float = 0.03,
67
67
  allowed_chains: Optional[List[str]] = None,
68
- ):
68
+ ) -> None:
69
69
  """Initialize the TokenQuote skill with configuration options."""
70
70
  super().__init__(skill_store=skill_store)
71
71
  self.default_slippage = default_slippage
@@ -78,7 +78,7 @@ class TokenQuote(LiFiBaseTool):
78
78
  from_token: str,
79
79
  to_token: str,
80
80
  from_amount: str,
81
- slippage: float = None,
81
+ slippage: Optional[float] = None,
82
82
  **kwargs,
83
83
  ) -> str:
84
84
  """Get a quote for token transfer."""