await run_multimodal_agent(ctx, participant) Fil...
# ask-ai
b
await run_multimodal_agent(ctx, participant) File “/Users/madhavsharma/uplevel-livekit-worker/app.py”, line 97, in run_multimodal_agent await session.start( ...<6 lines>... ) File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/opentelemetry/util/_decorator.py”, line 71, in async_wrapper return await func(*args, **kwargs) # type: ignore ^^^^^^^^^^^^^^^^^^^^^^^^^^^ File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/agents/voice/agent_session.py”, line 502, in start await asyncio.gather(*tasks) File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/agents/voice/agent_session.py”, line 844, in _update_activity await self._activity.start() File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/agents/voice/agent_activity.py”, line 378, in start await self._start_session() File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/agents/voice/agent_activity.py”, line 453, in _start_session await self._rt_session.update_tools(self.tools) File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/plugins/google/beta/realtime/realtime_api.py”, line 431, in update_tools new_declarations: list[types.FunctionDeclaration] = to_fnc_ctx(tools) ~~~~~~~~~~^^^^^^^ File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/plugins/google/utils.py”, line 40, in to_fnc_ctx tools.append(_build_gemini_fnc(fnc)) ~~~~~~~~~~~~~~~~~^^^^^ File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/plugins/google/utils.py”, line 104, in _build_gemini_fnc fnc = llm.utils.build_legacy_openai_schema(function_tool, internally_tagged=True) File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/agents/llm/utils.py”, line 192, in build_legacy_openai_schema model = function_arguments_to_pydantic_model(function_tool) File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/agents/llm/utils.py”, line 310, in function_arguments_to_pydantic_model type_hint = type_hints[param_name] ~~~~~~~~~~^^^^^^^^^^^^ what’s error
t
Thanks for reaching out, Madhav. I'm an AI assistant and I'm here to help. Give me a moment while I research this topic.
Hey there! The error you're seeing happens because the code is trying to grab a type hint for a parameter that isn't actually in the
type_hints
dictionary, which causes a KeyError. This usually pops up when a function parameter doesn’t have a type hint defined. Here are a few friendly ways to fix this: • Check if the Parameter Exists First: Before you access the type hint, just check if the parameter is in `type_hints`:
Copy code
if param_name in type_hints:
    type_hint = type_hints[param_name]
else:
    type_hint = None
Use the
get()
Method:
This is a neat trick — use the dictionary’s
get()
method with a default value to dodge that KeyError:
Copy code
type_hint = type_hints.get(param_name, None)
Skip Parameters Without Type Hints: If it’s okay to move on without some type hints, just skip those parameters:
Copy code
if param_name not in type_hints:
    continue
type_hint = type_hints[param_name]
These little tweaks help your code handle missing type hints smoothly, so you won’t run into that error again. Hope that helps!
b
2025-08-11 114329,916 - ERROR livekit.agents - unhandled exception while running the job task Traceback (most recent call last): File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/opentelemetry/util/_decorator.py”, line 71, in async_wrapper return await func(*args, **kwargs) # type: ignore ^^^^^^^^^^^^^^^^^^^^^^^^^^^ File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/agents/ipc/job_proc_lazy_main.py”, line 240, in _traceable_entrypoint await self._job_entrypoint_fnc(job_ctx) File “/Users/madhavsharma/uplevel-livekit-worker/app.py”, line 67, in entrypoint await run_multimodal_agent(ctx, participant) File “/Users/madhavsharma/uplevel-livekit-worker/app.py”, line 97, in run_multimodal_agent await session.start( ...<6 lines>... ) this is the error
t
Hey there! That error message, "unhandled exception while running the job task," usually pops up when something unexpected happens inside the job task and it’s not caught properly. This can be due to things like uncaught exceptions, the job being in a weird state, or even resource hiccups. Here’s how you can tackle it: • Add Error Handling: Wrap your job task code in
try/except
blocks to catch those exceptions and handle them gracefully. • Implement Proper Cleanup: Make sure you call
job_ctx.connect()
before your job starts and use
job_ctx.shutdown()
to clean up afterward. • Review Logs: Take a peek at the logs for any specific exception details—that usually helps pinpoint what’s going wrong. Here’s a quick example:
Copy code
@tracer.start_as_current_span("job_entrypoint")
async def job_entry(job_ctx: JobContext):
    try:
        # Your job code here
        job = job_ctx.job
        current_span = trace.get_current_span()
        current_span.set_attribute(trace_types.ATTR_JOB_ID, job.id)
    except Exception as e:
        logger.error("Unhandled exception in job task", exc_info=e)
        await job_ctx.shutdown("Unexpected error occurred")
    finally:
        await job_ctx.shutdown("Job task completed")
If you want, I’m here to help you dig deeper or clarify anything about the job task. Just let me know!
b
class Assistant(Agent): def *__init__*(self, instructions, _chat_ctx_=None) -> None: super().__init__(instructions=instructions, _chat_ctx_=_chat_ctx_,) this code above is working fine class Assistant(Agent): def *__init__*(self, instructions, _chat_ctx_=None) -> None: super().__init__(instructions=instructions, _chat_ctx_=_chat_ctx_, tools=[read_user_code, clear_user_codepad]) this is causing error from livekit.agents import Agent, function_tool, RunContext, get_job_context from typing import Dict, Any from utils.session_store import get_session_editor_content import logging logger = logging.getLogger(name) @function_tool() async def *read_user_code*( context,): “”"Read the current code written by the user in the editor. This tool allows the agent to access and analyze the code that the user has written in their editor during the interview session. Use this tool when you need to: - Review the user’s code implementation - Provide feedback on their coding approach - Help debug issues in their code - Understand their solution to continue the interview - Analyze code quality and suggest improvements Returns: The current code content from the user’s editor as a string. Returns an empty string if no code has been written yet. “”" _try_: # Get the current editor content from session storage code_content = get_session_editor_content() if not code_content or code_content.strip() == “”: logger.info(“No code found in editor”) return “The editor is currently empty. The user hasn’t written any code yet.” logger.info(f”Retrieved code from editor (length: {len(code_content)} characters)“) # Return the code with some formatting for better LLM understanding return f”“”Here is the current code from the user’s editor:
Copy code
{code_content}
“”" except Exception as e: logger.error(f”Error reading user code: {e}“) return f”Error reading user code: {str(e)}. The editor content might not be available.” from livekit.agents import Agent, function_tool, get_job_context, ToolError @function_tool async def *clear_user_codepad*(context): _try_: # Access the Room instance room = get_job_context().room if not room: raise Exception(“Room not available”) # Define the destination participant identity participant_identity = next(iter(room.remote_participants.keys())) # Perform the RPC call response = await room.local_participant.perform_rpc( _destination_identity_=participant_identity, method=“clear_user_codepad”, payload=“”, _response_timeout_=5.0 ) return response except Exception as e: raise ToolError(f”RPC clear_user_codepad call failed: {e}“) here’s tool code
t
Hey there! This error pops up because adding tools directly inside the
super().__init__
call in your Agent class isn’t quite the right way to do it. Instead, tools need to be passed properly through the
tools
parameter or set up using the
@function_tool
decorator. Here’s how you can fix it: • Using the
@function_tool
Decorator:
Just define your methods inside the agent class and decorate them with
@function_tool()
to register them as tools.
Copy code
class MyAgent(Agent):
    @function_tool()
    async def my_tool(self, context: RunContext, arg: str) -> str:
        return "Result"
Passing Tools During Initialization: When you initialize, pass a list of your tool functions to the
tools
parameter inside
super().__init__()
.
Copy code
class MyAgent(Agent):
    def __init__(self):
        super().__init__(
            tools=[read_user_code, clear_user_codepad],
        )
Just make sure your tools are always passed as a list to the
tools
parameter, and try not to add tool-related arguments directly to
super().__init__()
unless you’re using the right parameter. Hope this helps!
b
from livekit.agents import Agent, function_tool, RunContext, get_job_context from typing import Dict, Any from utils.session_store import get_session_editor_content import logging logger = logging.getLogger(name) from livekit.agents import Agent, function_tool, get_job_context, ToolError class Assistant(Agent): @function_tool() async def *read_user_code*( self, context,): “”"Read the current code written by the user in the editor. This tool allows the agent to access and analyze the code that the user has written in their editor during the interview session. Use this tool when you need to: - Review the user’s code implementation - Provide feedback on their coding approach - Help debug issues in their code - Understand their solution to continue the interview - Analyze code quality and suggest improvements Returns: The current code content from the user’s editor as a string. Returns an empty string if no code has been written yet. “”" _try_: # Get the current editor content from session storage code_content = get_session_editor_content() if not code_content or code_content.strip() == “”: logger.info(“No code found in editor”) return “The editor is currently empty. The user hasn’t written any code yet.” logger.info(f”Retrieved code from editor (length: {len(code_content)} characters)“) # Return the code with some formatting for better LLM understanding return f”“”Here is the current code from the user’s editor:
Copy code
{code_content}
“”" except Exception as e: logger.error(f”Error reading user code: {e}“) return f”Error reading user code: {str(e)}. The editor content might not be available.” @function_tool async def *clear_user_codepad*(self,context): _try_: # Access the Room instance room = get_job_context().room if not room: raise Exception(“Room not available”) # Define the destination participant identity participant_identity = next(iter(room.remote_participants.keys())) # Perform the RPC call response = await room.local_participant.perform_rpc( _destination_identity_=participant_identity, method=“clear_user_codepad”, payload=“”, _response_timeout_=5.0 ) return response except Exception as e: raise ToolError(f”RPC clear_user_codepad call failed: {e}“) def *__init__*(self, instructions, _chat_ctx_=None) -> None: super().__init__(instructions=instructions, _chat_ctx_=_chat_ctx_, tools=[self.clear_user_codepad, self.read_user_code]) this is throwing error
t
Hey there! The error you're seeing happens because
self.clear_user_codepad
and
self.read_user_code
are being passed directly as tools in the
super().__init__
call. But for LiveKit to recognize them properly, these tools need to be decorated the right way. Here’s what you can do to fix it: • Make sure both methods have the
@function_tool()
decorator. • Then, pass these decorated methods to the
tools
parameter inside
super().__init__()
. Here’s how it should look:
Copy code
class Assistant(Agent):
    def __init__(self, instructions, chat_ctx=None):
        super().__init__(
            instructions=instructions,
            chat_ctx=chat_ctx,
            tools=[self.clear_user_codepad, self.read_user_code]
        )

    @function_tool()
    async def clear_user_codepad(self, context):
        # Implementation here
        pass

    @function_tool()
    async def read_user_code(self, context):
        # Implementation here
        pass
This way, your methods get properly registered as tools, and that pesky error will be gone. Hope this helps!
b
I have already done this
t
Hey there! If you’ve already decorated your tools with
@function_tool
but are still running into errors, no worries—here are a few more things to check that might help clear things up: • Unique Tool Names: Make sure each tool has its own unique name. You can set this using the
name
parameter inside
@function_tool
. • Tool Registration: Double-check that all your tools are properly passed to the
tools
parameter in
super().__init__
. • Dynamic Tool Addition: If the problem sticks around, try adding tools dynamically after initialization with
self.update_tools([self.clear_user_codepad, self.read_user_code])
. • Inheritance Issues: Make sure
super().__init__
is called correctly in your subclasses and that tools aren’t accidentally getting overridden. If none of these tips do the trick, feel free to share the exact error message or any extra details—you’re not alone, and I’m here to help!
b
enai_schema model = function_arguments_to_pydantic_model(function_tool) File “/Users/madhavsharma/uplevel-livekit-worker/venv/lib/python3.13/site-packages/livekit/agents/llm/utils.py”, line 310, in function_arguments_to_pydantic_model type_hint = type_hints[param_name] still getting this error
t
It looks like the error happens because the code is trying to grab a type hint for a parameter that isn’t in the
type_hints
dictionary. No worries though—you can fix this by updating your code to handle cases where a type hint might be missing, by giving it a default value. Here’s how you can update the part where you retrieve the type hint:
Copy code
from typing import Any

# Inside function_arguments_to_pydantic_model
type_hint = type_hints.get(param_name, Any)
This way, if a parameter doesn’t have a type hint, it will just use
Any
by default. That’ll stop the error from popping up and let your model get created smoothly.