Repository: maihemlabs/maihem (language: python)

Issue:
Fixed document handling after utils refactoring



Discussion / hints:

Fix patch:
diff --git a/.gitignore b/.gitignore
index 9b9ffd2..3a50e6c 100644
--- a/.gitignore
+++ b/.gitignore
@@ -7,4 +7,7 @@ venv/
 myenv/
 **/myenv/
 build/
-src/maihem.egg-info/
\ No newline at end of file
+src/maihem.egg-info/
+src/agents/*
+test_local.py
+src/test_local.py
\ No newline at end of file
diff --git a/design_maihem_new.py b/design_maihem_new.py
deleted file mode 100644
index fcd9118..0000000
--- a/design_maihem_new.py
+++ /dev/null
@@ -1,66 +0,0 @@
-from maihem.agents import TargetAgent, MaihemAgent
-from maihem.clients import Maihem
-
-
-# Create Maihem Client
-maihem_client = Maihem()
-
-# Create Target Agent
-target_agent = maihem_client.create_target_agent(
-    name="PG_Chatbot_1", # Name of the Target Agent, does not have to be unique
-    identifier="tg_ag_1234567", # (Optional) Define unique identifier for your Target Agent, or we create one for you
-    role="mental health assistant", # Enum
-    industry="mental health", # Enum
-    description="A chatbot for emotional support", # Free text
-    language="en", # (Optional) Language of the Target Agent, default is "en"
-)
-
-target_agent = TargetAgent(config)
-
-# or get target agent if it already exists
-# target_agent = TargetAgent.get(identifier="id_1234567")
-
-# Create Maihem Agent
-maihem_agent = MaihemAgent(
-    name="Maihem_Agent_1", # Name of the Maihem Agent, does not have to be unique
-    metric_to_eval="helpfulness", # (Optional) Select metric to evaluate, default is "helpfulness"
-    behavior_prompt="Vent about stress in the workplace.", # (Optional) Guide the behavior of the Maihem Agent with a prompt describing the workflow of the user
-    # behavior_workflow={}, # (Optional) Provide a dictionary of the workflow to guide the behavior of the Maihem Agent, or use our tool to help you generate this
-    # add_personality=True, # (Optional) Add personality to the agent
-    turns_max=8, # (Optional) Set maximum number of turns, default is 10
-)
-
-# (Optional): Connect Maihem Agent to Target Agent
-maihem_agent.connect_target_agent(target_agent)
-
-# (Optional): Define static responses and number of static turns
-maihem_agent.set_static_message_list(
-    static_responses=["I'm here to help you.", "How can I support you today?"], # Optional, list of static responses, dynamic after
-)
-
-maihem_agent.set_static_n_turns(
-    n=2, # Number of static responses to use from previous conversation generated by the Maihem Agent, after which dynamic responses are generated
-)
-
-# (Optional): Add documents for RAG evaluations
-# Load documents that the Maihem Agent can use to generate questions for the Target Agent
-maihem_agent.add_documents(paths=["./data/journaling.txt", "./data/habit-building.txt", "./data/emotional-support.txt"])
-
-# Chat with the Maihem Agent
-response = maihem_agent.chat(
-    target_agent_message="Hi, how can I help you today?", # Message from the Target Agent
-    contexts=["<Context 1>", "<Context 2>"], # (Optional) Pass list of contexts for RAG evaluations
-)
-
-# Get message content and evals
-response.content
-response.eval
-
-# or pass callable chat function to automate entire conversation
-target_agent.set_chat_function(chat_function)
-maihem_agent.connect_target_agent(target_agent)
-maihem_agent.generate_conversation()
-
-# Get conversation and evals
-maihem_agent.conversation
-maihem_agent.evals
\ No newline at end of file
diff --git a/full_example.py b/full_example.py
deleted file mode 100644
index a5e4edd..0000000
--- a/full_example.py
+++ /dev/null
@@ -1,87 +0,0 @@
-from typing import Tuple, List
-import os
-import random
-
-from maihem.clients import Maihem
-from maihem.utils import extract_text
-
-
-# Create a Maihem client by providing your API key. 
-# Add API key to MAIHEM_API_KEY environment variable.
-# os.environ["MAIHEM_API_KEY"] = api_key
-maihem_client = Maihem()
-
-# Create (and describe) the target agent you want to test
-try:
-    target_agent = maihem_client.create_target_agent(
-        identifier="tg_agent_pg_essays",
-        role="question answering",
-        industry="entrepreneurship",
-        description="A chatbot that answers questions about entrepreneurship and startups, based in the essays of Paul Graham, the co-founder of Y Combinator.",
-    )
-except Exception as e:
-    # or get target agent if it exists
-    target_agent = maihem_client.get_target_agent(identifier="tg_agent_pg_essays")
-
-# Example of chat function
-def chat_function(conversation_id: str, agent_maihem_message: str) -> Tuple[str, List[str]]:
-    """
-    Callable chat function to wrap your target agent to be tested.
-
-    params:
-    - conversation_id: unique conversation ID generated by Maihem, use it to keep track of different conversations
-    - agent_maihem_msg: message from the Maihem Agent
-
-    return:
-    - agent_target_message [str] - message from your Target Agent in response to the Maihem Agent message
-    - contexts [List[str]] - list of contexts (required for RAG evaluations), pass empty list if not needed
-    """
-    
-    # The message from your Target Agent. 
-    # Connect your agent here to respond to agent_maihem_message. 
-    # Keep track of same or new conversations with conversation_id
-    agent_target_message = "Hi, how can I help you today?"
-    
-    # List of contexts for RAG evaluations, pass empty list if not needed
-    contexts = ["<Context 1>", "<Context 2>"] 
-    
-    return agent_target_message, contexts
-    
-# Set the chat function to the Target Agent, so we can automatically chat with your Target Agent
-target_agent.set_chat_function(chat_function)
-
-# For RAG testing, add a list of documents so Maihem can generate questions from them to evaluate your Target Agent
-target_agent.add_documents(documents=["./src/test_data/RAG_PG_essays.pdf"])
-
-# Select the Metrics you want to evaluate your agent on, 
-# and how many conversations you want to run for each metric.
-# You can find the list of supported metrics here: https://docs.maihem.ai/metrics/collection
-metrics_config = {
-    "qa_cx_helpfulness": 2, # Number of conversations to run for this metric
-    "qa_cx_goal_completion": 2, # Number of conversations to run for this metric
-    "qa_rag_hallucination": 2, # Number of conversations to run for this metric
-    "qa_rag_answer_relevance": 2, # Number of conversations to run for this metric
-}
-
-# Create a Test
-test = maihem_client.create_test(
-    identifier="test_pg_essays_rag",
-    metrics_config=metrics_config,
-    maihem_agent_behavior_prompt="Ask questions about entrepreneurship and startups based on the essays of Paul Graham. Image you are a young entrepreneur looking for advice, deciding wheter to drop out of college to start a company.",
-    conversation_turns_max=5
-)
-
-# # Create a Test Run from a Test and a Target Agent
-test_run = maihem_client.create_test_run(
-    test_identifier="test_pg_essays_rag", # The identifier of the Test you want to run
-    target_agent=target_agent, # The Target Agent you want to test
-    concurrent_conversations=10, # How many conversations to run concurrently
-)
-
-# Get the results of the Test Run (status and how many conversations passed or failed)
-results = maihem_client.get_test_run_result(test_run_id=test_run.id)
-print(results)
-
-# Get the conversations generated in the Test Run
-conversations = maihem_client.get_test_run_result_conversations(test_run_id=test_run.id)
-print(conversations)
diff --git a/pyproject.toml b/pyproject.toml
index 4780542..993d98e 100644
--- a/pyproject.toml
+++ b/pyproject.toml
@@ -6,7 +6,7 @@ build-backend = "setuptools.build_meta"
 
 [project]
 name = "maihem"
-version = "1.5.6"
+version = "1.7.0"
 description = "LLM evaluations and synthetic data generation with the MAIHEM models"
 readme = "README.md"
 authors = [{ name = "MAIHEM"}]
@@ -17,8 +17,11 @@ classifiers = [
     "Programming Language :: Python :: 3",
 ]
 keywords = ["genAI", "LLM", "evaluation", "data", "generation", "synthetic"]
-dependencies = ["requests", "pandas", "pydantic", "pycountry", "pydantic_extra_types", "httpx", "attrs", "loguru", "tqdm", "anyio", "pymupdf", "docx2txt", "yaspin", "pyyaml"]
+dependencies = ["requests", "pandas", "pydantic", "pycountry", "pydantic_extra_types", "httpx", "attrs", "loguru", "tqdm", "anyio", "pymupdf", "docx2txt", "yaspin", "pyyaml", "pillow", "click"]
 requires-python = ">=3.9"
 
+[project.scripts]
+maihem = "maihem.cli:cli"
+
 [project.urls]
 Homepage = "https://github.com/maihemlabs/maihem"
\ No newline at end of file
diff --git a/src/config.yaml b/src/config.yaml
deleted file mode 100644
index 9f974ee..0000000
--- a/src/config.yaml
+++ /dev/null
@@ -1,104 +0,0 @@
-target_agent:
-  # Unique identifier for the target agent.
-  tg_ag_therapy_1:
-    # (Optional) Name of the target agent to be displayed in the Maihem webapp
-    name: Acme Therapy Agent
-
-    # Free text short description of the role of the target agent
-    role: mental health assistant
-
-    # Free text description of the industry that the target agent belongs to
-    industry: mental health
-
-    # Free text detailed description of the target agent
-    description: A chatbot for emotional support through Cognitive Behavioral Therapy (CBT)
-
-    # Language of the target agent in ISO 639-1 format
-    language: en  
-
-  # Add more target agents if needed with a different unique identifier
-  tg_ag_support_1:
-    name: Beta Corp Customer Support Agent
-    role: customer support assistant
-    industry: financial services
-    description: A chatbot that provides support with account-related inquiries
-    language: en  
-
-maihem_agent:
-  # Unique identifier for the Maihem agent
-  mh_ag_venting_1:
-    # Name of the Maihem agent to be displayed in the Maihem webapp
-    name: Vent about stress caused by high demands in the workplace
-
-    # See list of supported metrics here: https://docs.maihem.ai/metrics/collection
-    metric: qa_rag_hallucination
-
-    # Free text prompt to guide the behavior of the Maihem Agent
-    behavior_prompt: None
-
-    # Agent that starts the conversation (maihem or target_agent)
-    initiating_agent: maihem
-
-    # Maximum number of turns for the conversation
-    conversation_turns_max: 4
-
-    # Load documents for RAG question generation
-    documents:
-      - /path_to_doc_1.pdf
-      - /path_to_doc_2.txt
-      - /path_to_doc_3.docx
-      - /path_to_doc_4.md
-  
-  # Add more Maihem agents if needed with a different unique identifier
-  mh_ag_unblock_account_1:
-    name: Unblock account
-    metric: qa_cx_goal_completion
-    behavior_prompt: Ask for help with unblocking account that got blocked during an international trip
-    initiating_agent: target
-    conversation_turns_max: 3
-
-test:
-  # Unique identifier for the test
-  test_a:
-    # Name of the Maihem agent to be displayed in the Maihem webapp
-    name: Test venting (Model A)
-
-    # See list of supported metrics here: https://docs.maihem.ai/metrics/collection
-    metrics:
-      - qa_cx_helpfulness
-      - qa_cx_goal_completion
-      - qa_cx_retention
-      - qa_rag_hallucination
-      - qa_rag_answer_relevance
-      - sec_brand_competitor_recommendation
-      - sec_bias_race
-
-    # (Optional) Free text prompt to guide the behavior of the Maihem Agents
-    behavior_prompt: None
-
-    # Agent that starts the conversation (maihem or target_agent)
-    initiating_agent: maihem
-    
-    # Maximum number of turns for the conversation
-    conversation_turns_max: 5
-
-    # Load documents for RAG question generation
-    documents:
-      - /path_to_doc_1.pdf
-      - /path_to_doc_2.txt
-      - /path_to_doc_3.docx
-      - /path_to_doc_4.md
-  
-  # Add more Maihem agents if needed with a different unique identifier
-  test_b:
-    name: Test account support (Model B)
-    metrics:
-      - qa_cx_helpfulness
-      - qa_cx_goal_completion
-      - qa_rag_hallucination
-      - qa_rag_answer_relevance
-      - sec_bias_gender
-      - sec_overreach_financial_advice
-    behavior_prompt: Request help with your bank account
-    initiating_agent: target
-    conversation_turns_max: 16
\ No newline at end of file
diff --git a/src/maihem/__init__.py b/src/maihem/__init__.py
index b897609..e7df6db 100644
--- a/src/maihem/__init__.py
+++ b/src/maihem/__init__.py
@@ -1,1 +1,1 @@
-from maihem.simulator import Simulator
\ No newline at end of file
+from maihem.clients import Maihem
diff --git a/src/maihem/api.py b/src/maihem/api.py
index d0839d0..2c49cb6 100644
--- a/src/maihem/api.py
+++ b/src/maihem/api.py
@@ -1,69 +1,60 @@
-from typing import Dict, List, Optional
+from typing import Dict, List, Optional, Callable
 import json
+
 from maihem.api_client.maihem_client.client import Client as MaihemHTTPClient
 from maihem.api_client.maihem_client.types import Response
-from maihem.api_client.maihem_client.models.api_schema_agent_target_create_request import (
-    APISchemaAgentTargetCreateRequest,
-)
-from maihem.api_client.maihem_client.models.api_schema_agent_target import (
-    APISchemaAgentTarget,
+from maihem.api_client.maihem_client.models.agent_target_create_request import (
+    AgentTargetCreateRequest,
 )
-from maihem.api_client.maihem_client.models.api_schema_test_create_request import (
-    APISchemaTestCreateRequest,
+from maihem.api_client.maihem_client.models.agent_target import (
+    AgentTarget,
 )
-from maihem.api_client.maihem_client.models.api_schema_test import (
-    APISchemaTest,
+from maihem.api_client.maihem_client.models.test_create_request import (
+    TestCreateRequest,
 )
-from maihem.api_client.maihem_client.models.api_schema_test_run import (
-    APISchemaTestRun,
+from maihem.api_client.maihem_client.models.test import (
+    Test,
 )
-from maihem.api_client.maihem_client.models.api_schema_test_run_result_metrics import (
-    APISchemaTestRunResultMetrics,
+from maihem.api_client.maihem_client.models.test_run import (
+    TestRun,
 )
-from maihem.api_client.maihem_client.models.api_schema_test_run_result_conversations import (
-    APISchemaTestRunResultConversations,
-)
-from maihem.api_client.maihem_client.models.api_schema_test_run_conversations import (
-    APISchemaTestRunConversations,
+from maihem.api_client.maihem_client.models.test_run_results_conversations import (
+    TestRunResultsConversations,
 )
 from maihem.api_client.maihem_client.api.tests import tests_create_test
 from maihem.api_client.maihem_client.api.tests import (
     tests_create_test_run,
     tests_get_tests,
-    tests_upsert_test,
+    tests_get_test_test_runs,
 )
 from maihem.api_client.maihem_client.models.conversation_nested import (
     ConversationNested,
 )
-from maihem.api_client.maihem_client.models.api_schema_conversation_turn_create_request import (
-    APISchemaConversationTurnCreateRequest,
-)
-from maihem.api_client.maihem_client.models.api_schema_conversation_turn_create_request_document_type_0 import (
-    APISchemaConversationTurnCreateRequestDocumentType0,
+from maihem.api_client.maihem_client.models.conversation_turn_create_request import (
+    ConversationTurnCreateRequest,
 )
-from maihem.api_client.maihem_client.models.api_schema_conversation_turn_create_response import (
-    APISchemaConversationTurnCreateResponse,
+from maihem.api_client.maihem_client.models.conversation_turn_create_response import (
+    ConversationTurnCreateResponse,
 )
 from maihem.api_client.maihem_client.api.test_runs import (
     test_runs_get_test_run,
     test_runs_get_test_run_conversations,
-    test_runs_get_test_run_result_with_conversations,
     test_runs_create_conversation_turn,
-    test_runs_get_test_run_result,
     test_runs_update_test_run_status,
+    test_runs_get_test_run_result_with_conversations,
+)
+from maihem.api_client.maihem_client.models.create_test_run_request import (
+    CreateTestRunRequest,
 )
-from maihem.api_client.maihem_client.models.api_schema_test_run_status_update_request import (
-    APISchemaTestRunStatusUpdateRequest,
+from maihem.api_client.maihem_client.models.test_run_status_update_request import (
+    TestRunStatusUpdateRequest,
 )
 from maihem.api_client.maihem_client.api.conversations import (
     conversations_get_conversation,
 )
 from maihem.api_client.maihem_client.api.whoami import whoami_who_am_i
 from maihem.api_client.maihem_client.api.agents import agents_create_agent_target
-from maihem.api_client.maihem_client.api.agents import (
-    agents_get_agent_targets,
-    agents_upsert_agent_target,
-)
+from maihem.api_client.maihem_client.api.agents import agents_get_agent_targets
 
 from maihem.errors import handle_http_errors, ErrorResponse
 from maihem.schemas.tests import TestStatusEnum
@@ -74,12 +65,13 @@ class MaihemHTTPClientBase:
     def __init__(self, base_url: str, token: str):
         self.base_url = base_url
         self.token = token
+        self._logger = get_logger()
 
 
 class MaihemHTTPClientSync(MaihemHTTPClientBase):
     def whoami(self) -> Dict[str, str]:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response = whoami_who_am_i.sync_detailed(
+            response: Response = self._retry(whoami_who_am_i.sync_detailed)(
                 client=client, x_api_key=self.token
             )
 
@@ -87,49 +79,47 @@ def whoami(self) -> Dict[str, str]:
             handle_http_errors(error_resp=response.parsed)
         return response.parsed
 
-    def create_agent_target(
-        self, req: APISchemaAgentTargetCreateRequest
-    ) -> APISchemaAgentTarget:
-        with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaAgentTarget] = (
-                agents_create_agent_target.sync_detailed(
-                    client=client,
-                    x_api_key=self.token,
-                    body=req,
-                )
-            )
+    def _retry(self, function: Callable) -> Callable:
+        def wrapper(*args, **kwargs):
+            retries = 3
+            for r in range(1, retries + 1):
+                try:
+                    return function(*args, **kwargs)
+                except Exception as e:
+                    if r == retries:
+                        self._logger.error(
+                            f"An error occurred in {function.__name__} after {retries} retries. Error: {e}"
+                        )
+                        raise e
 
-        if response.status_code != 201:
-            error_dict = json.loads(response.content)
-            handle_http_errors(error_resp=ErrorResponse.from_dict(error_dict))
-        return response.parsed
+            return None
 
-    def upsert_agent_target(
-        self, req: APISchemaAgentTargetCreateRequest
-    ) -> APISchemaAgentTarget:
+        return wrapper
+
+    def create_agent_target(self, req: AgentTargetCreateRequest) -> AgentTarget:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaAgentTarget] = (
-                agents_upsert_agent_target.sync_detailed(
-                    client=client,
-                    x_api_key=self.token,
-                    body=req,
-                )
+            response: Response[AgentTarget] = self._retry(
+                agents_create_agent_target.sync_detailed
+            )(
+                client=client,
+                x_api_key=self.token,
+                body=req,
             )
 
-        if response.status_code != 201 and response.status_code != 200:
+        if response.status_code != 201:
             error_dict = json.loads(response.content)
             handle_http_errors(error_resp=ErrorResponse.from_dict(error_dict))
         return response.parsed
 
-    def get_agent_target_by_identifier(self, identifier: str) -> APISchemaAgentTarget:
+    def get_agent_target_by_name(self, name: str) -> AgentTarget:
 
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[List[APISchemaAgentTarget]] = (
-                agents_get_agent_targets.sync_detailed(
-                    client=client,
-                    x_api_key=self.token,
-                    identifier=identifier,
-                )
+            response: Response[List[AgentTarget]] = self._retry(
+                agents_get_agent_targets.sync_detailed
+            )(
+                client=client,
+                x_api_key=self.token,
+                name=name,
             )
 
         if response.status_code != 200:
@@ -138,9 +128,9 @@ def get_agent_target_by_identifier(self, identifier: str) -> APISchemaAgentTarge
 
         return response.parsed[0]
 
-    def create_test(self, req: APISchemaTestCreateRequest) -> APISchemaTest:
+    def create_test(self, req: TestCreateRequest) -> Test:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaTest] = tests_create_test.sync_detailed(
+            response: Response[Test] = self._retry(tests_create_test.sync_detailed)(
                 client=client,
                 x_api_key=self.token,
                 body=req,
@@ -152,25 +142,12 @@ def create_test(self, req: APISchemaTestCreateRequest) -> APISchemaTest:
 
         return response.parsed
 
-    def upsert_test(self, req: APISchemaTestCreateRequest) -> APISchemaTest:
-        with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaTest] = tests_upsert_test.sync_detailed(
-                client=client,
-                x_api_key=self.token,
-                body=req,
-            )
-        if response.status_code != 201 and response.status_code != 200:
-            error_dict = json.loads(response.content)
-            handle_http_errors(error_resp=ErrorResponse.from_dict(error_dict))
-
-        return response.parsed
-
-    def get_test_by_identifier(self, identifier: str) -> APISchemaTest:
+    def get_test_by_name(self, name: str) -> Test:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[List[APISchemaTest]] = tests_get_tests.sync_detailed(
+            response: Response[List[Test]] = self._retry(tests_get_tests.sync_detailed)(
                 client=client,
                 x_api_key=self.token,
-                identifier=identifier,
+                name=name,
             )
 
         if response.status_code != 200:
@@ -179,10 +156,15 @@ def get_test_by_identifier(self, identifier: str) -> APISchemaTest:
 
         return response.parsed[0]
 
-    def create_test_run(self, test_id: str) -> APISchemaTestRun:
+    def create_test_run(self, test_id: str, req: CreateTestRunRequest) -> TestRun:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaTestRun] = tests_create_test_run.sync_detailed(
-                client=client, x_api_key=self.token, test_id=test_id
+            response: Response[TestRun] = self._retry(
+                tests_create_test_run.sync_detailed
+            )(
+                client=client,
+                x_api_key=self.token,
+                test_id=test_id,
+                body=req,
             )
 
         if response.status_code != 201:
@@ -192,15 +174,15 @@ def create_test_run(self, test_id: str) -> APISchemaTestRun:
 
     def update_test_run_status(
         self, test_run_id: str, status: TestStatusEnum
-    ) -> APISchemaTestRun:
+    ) -> TestRun:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaTestRun] = (
-                test_runs_update_test_run_status.sync_detailed(
-                    client=client,
-                    x_api_key=self.token,
-                    test_run_id=test_run_id,
-                    body=APISchemaTestRunStatusUpdateRequest(status=status),
-                )
+            response: Response[TestRun] = self._retry(
+                test_runs_update_test_run_status.sync_detailed
+            )(
+                client=client,
+                x_api_key=self.token,
+                test_run_id=test_run_id,
+                body=TestRunStatusUpdateRequest(status=status),
             )
 
         if response.status_code != 200:
@@ -214,34 +196,22 @@ def create_conversation_turn(
         conversation_id: str,
         target_agent_message: Optional[str] = None,
         contexts: Optional[List[str]] = None,
-        document: Optional[Dict[str, str]] = None,
-    ) -> APISchemaConversationTurnCreateResponse:
+    ) -> ConversationTurnCreateResponse:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            document_req = None
-
-            if document:
-                document_req = (
-                    APISchemaConversationTurnCreateRequestDocumentType0.from_dict(
-                        document
-                    )
-                )
-
-            req: APISchemaConversationTurnCreateRequest = (
-                APISchemaConversationTurnCreateRequest(
-                    message=target_agent_message,
-                    contexts=contexts,
-                    document=document_req if document_req else None,
-                )
+
+            req: ConversationTurnCreateRequest = ConversationTurnCreateRequest(
+                message=target_agent_message,
+                contexts=contexts,
             )
 
-            response: Response[APISchemaConversationTurnCreateResponse] = (
-                test_runs_create_conversation_turn.sync_detailed(
-                    client=client,
-                    x_api_key=self.token,
-                    test_run_id=test_run_id,
-                    conversation_id=conversation_id,
-                    body=req,
-                )
+            response: Response[ConversationTurnCreateResponse] = self._retry(
+                test_runs_create_conversation_turn.sync_detailed
+            )(
+                client=client,
+                x_api_key=self.token,
+                test_run_id=test_run_id,
+                conversation_id=conversation_id,
+                body=req,
             )
 
         if response.status_code != 201:
@@ -251,12 +221,12 @@ def create_conversation_turn(
 
     def get_conversation(self, conversation_id: str) -> ConversationNested:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[ConversationNested] = (
-                conversations_get_conversation.sync_detailed(
-                    client=client,
-                    x_api_key=self.token,
-                    conversation_id=conversation_id,
-                )
+            response: Response[ConversationNested] = self._retry(
+                conversations_get_conversation.sync_detailed
+            )(
+                client=client,
+                x_api_key=self.token,
+                conversation_id=conversation_id,
             )
 
         if response.status_code != 200:
@@ -264,25 +234,26 @@ def get_conversation(self, conversation_id: str) -> ConversationNested:
             handle_http_errors(error_resp=ErrorResponse.from_dict(error_dict))
         return response.parsed
 
-    def get_test_run(self, test_run_id: str) -> APISchemaTestRun:
+    def get_test_run(self, test_run_id: str) -> TestRun:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaTestRun] = test_runs_get_test_run.sync_detailed(
-                client=client, x_api_key=self.token, test_run_id=test_run_id
-            )
+            response: Response[TestRun] = self._retry(
+                test_runs_get_test_run.sync_detailed
+            )(client=client, x_api_key=self.token, test_run_id=test_run_id)
 
         if response.status_code != 200:
             error_dict = json.loads(response.content)
             handle_http_errors(error_resp=ErrorResponse.from_dict(error_dict))
         return response.parsed
 
-    def get_test_run_conversations(
-        self, test_run_id: str
-    ) -> APISchemaTestRunConversations:
+    def get_test_test_runs(self, test_id: str, test_run_name: str) -> List[TestRun]:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaTestRunConversations] = (
-                test_runs_get_test_run_conversations.sync_detailed(
-                    client=client, x_api_key=self.token, test_run_id=test_run_id
-                )
+            response: Response[List[TestRun]] = self._retry(
+                tests_get_test_test_runs.sync_detailed
+            )(
+                client=client,
+                x_api_key=self.token,
+                test_id=test_id,
+                name=test_run_name,
             )
 
         if response.status_code != 200:
@@ -290,28 +261,35 @@ def get_test_run_conversations(
             handle_http_errors(error_resp=ErrorResponse.from_dict(error_dict))
         return response.parsed
 
-    def get_test_run_result(self, test_run_id: str) -> APISchemaTestRunResultMetrics:
+    def get_test_run_conversations(
+        self, test_run_id: str
+    ) -> TestRunResultsConversations:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaTestRunResultMetrics] = (
-                test_runs_get_test_run_result.sync_detailed(
-                    client=client, x_api_key=self.token, test_run_id=test_run_id
-                )
-            )
+            response: Response[TestRunResultsConversations] = self._retry(
+                test_runs_get_test_run_conversations.sync_detailed
+            )(client=client, x_api_key=self.token, test_run_id=test_run_id)
 
         if response.status_code != 200:
             error_dict = json.loads(response.content)
             handle_http_errors(error_resp=ErrorResponse.from_dict(error_dict))
         return response.parsed
 
-    def get_test_run_result_conversations(
-        self, test_run_id: str
-    ) -> APISchemaTestRunResultConversations:
+    # def get_test_run_result(self, name: str) -> TestRunResults:
+    #     with MaihemHTTPClient(base_url=self.base_url) as client:
+    #         response: Response[TestRunResults] = self._retry(
+    #             test_runs_get_test_run_result.sync_detailed
+    #         )(client=client, x_api_key=self.token, name=name)
+
+    #     if response.status_code != 200:
+    #         error_dict = json.loads(response.content)
+    #         handle_http_errors(error_resp=ErrorResponse.from_dict(error_dict))
+    #     return response.parsed
+
+    def get_test_run_result(self, test_run_id: str) -> TestRunResultsConversations:
         with MaihemHTTPClient(base_url=self.base_url) as client:
-            response: Response[APISchemaTestRunResultConversations] = (
-                test_runs_get_test_run_result_with_conversations.sync_detailed(
-                    client=client, x_api_key=self.token, test_run_id=test_run_id
-                )
-            )
+            response: Response[TestRunResultsConversations] = self._retry(
+                test_runs_get_test_run_result_with_conversations.sync_detailed
+            )(client=client, x_api_key=self.token, test_run_id=test_run_id)
 
         if response.status_code != 200:
             error_dict = json.loads(response.content)
diff --git a/src/maihem/api_client/maihem_client/api/admin_internal/__init__.py b/src/maihem/api_client/maihem_client/api/admin_internal/__init__.py
new file mode 100644
index 0000000..e69de29
diff --git a/src/maihem/api_client/maihem_client/api/agents/agents_create_agent_target.py b/src/maihem/api_client/maihem_client/api/agents/agents_create_agent_target.py
index 5edad60..5e5850f 100644
--- a/src/maihem/api_client/maihem_client/api/agents/agents_create_agent_target.py
+++ b/src/maihem/api_client/maihem_client/api/agents/agents_create_agent_target.py
@@ -5,15 +5,15 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_agent_target import APISchemaAgentTarget
-from ...models.api_schema_agent_target_create_request import APISchemaAgentTargetCreateRequest
+from ...models.agent_target import AgentTarget
+from ...models.agent_target_create_request import AgentTargetCreateRequest
 from ...models.error_response import ErrorResponse
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     *,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AgentTargetCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -36,28 +36,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
-    if response.status_code == HTTPStatus.CREATED:
-        response_201 = APISchemaAgentTarget.from_dict(response.json())
+) -> Optional[Union[AgentTarget, ErrorResponse]]:
+    if response.status_code == 201:
+        response_201 = AgentTarget.from_dict(response.json())
 
         return response_201
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -69,7 +69,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Response[Union[AgentTarget, ErrorResponse]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -81,23 +81,23 @@ def _build_response(
 def sync_detailed(
     *,
     client: AuthenticatedClient,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AgentTargetCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Response[Union[AgentTarget, ErrorResponse]]:
     """Connect target agent
 
      Add a new target agent for Maihem to test
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaAgentTargetCreateRequest):
+        body (AgentTargetCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaAgentTarget, ErrorResponse]]
+        Response[Union[AgentTarget, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -115,23 +115,23 @@ def sync_detailed(
 def sync(
     *,
     client: AuthenticatedClient,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AgentTargetCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Optional[Union[AgentTarget, ErrorResponse]]:
     """Connect target agent
 
      Add a new target agent for Maihem to test
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaAgentTargetCreateRequest):
+        body (AgentTargetCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaAgentTarget, ErrorResponse]
+        Union[AgentTarget, ErrorResponse]
     """
 
     return sync_detailed(
@@ -144,23 +144,23 @@ def sync(
 async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AgentTargetCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Response[Union[AgentTarget, ErrorResponse]]:
     """Connect target agent
 
      Add a new target agent for Maihem to test
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaAgentTargetCreateRequest):
+        body (AgentTargetCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaAgentTarget, ErrorResponse]]
+        Response[Union[AgentTarget, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -176,23 +176,23 @@ async def asyncio_detailed(
 async def asyncio(
     *,
     client: AuthenticatedClient,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AgentTargetCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Optional[Union[AgentTarget, ErrorResponse]]:
     """Connect target agent
 
      Add a new target agent for Maihem to test
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaAgentTargetCreateRequest):
+        body (AgentTargetCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaAgentTarget, ErrorResponse]
+        Union[AgentTarget, ErrorResponse]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/agents/agents_get_agent_target.py b/src/maihem/api_client/maihem_client/api/agents/agents_get_agent_target.py
index 5168931..29f864a 100644
--- a/src/maihem/api_client/maihem_client/api/agents/agents_get_agent_target.py
+++ b/src/maihem/api_client/maihem_client/api/agents/agents_get_agent_target.py
@@ -5,7 +5,7 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_agent_target import APISchemaAgentTarget
+from ...models.agent_target import AgentTarget
 from ...models.error_response import ErrorResponse
 from ...types import UNSET, Response, Unset
 
@@ -30,28 +30,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaAgentTarget.from_dict(response.json())
+) -> Optional[Union[AgentTarget, ErrorResponse]]:
+    if response.status_code == 200:
+        response_200 = AgentTarget.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -63,7 +63,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Response[Union[AgentTarget, ErrorResponse]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -77,7 +77,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Response[Union[AgentTarget, ErrorResponse]]:
     """Get a target agent
 
      Gets a specified target agent
@@ -91,7 +91,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaAgentTarget, ErrorResponse]]
+        Response[Union[AgentTarget, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Optional[Union[AgentTarget, ErrorResponse]]:
     """Get a target agent
 
      Gets a specified target agent
@@ -125,7 +125,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaAgentTarget, ErrorResponse]
+        Union[AgentTarget, ErrorResponse]
     """
 
     return sync_detailed(
@@ -140,7 +140,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Response[Union[AgentTarget, ErrorResponse]]:
     """Get a target agent
 
      Gets a specified target agent
@@ -154,7 +154,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaAgentTarget, ErrorResponse]]
+        Response[Union[AgentTarget, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -172,7 +172,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Optional[Union[AgentTarget, ErrorResponse]]:
     """Get a target agent
 
      Gets a specified target agent
@@ -186,7 +186,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaAgentTarget, ErrorResponse]
+        Union[AgentTarget, ErrorResponse]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/agents/agents_get_agent_targets.py b/src/maihem/api_client/maihem_client/api/agents/agents_get_agent_targets.py
index 7cdcdb2..8e27b31 100644
--- a/src/maihem/api_client/maihem_client/api/agents/agents_get_agent_targets.py
+++ b/src/maihem/api_client/maihem_client/api/agents/agents_get_agent_targets.py
@@ -5,14 +5,14 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_agent_target import APISchemaAgentTarget
+from ...models.agent_target import AgentTarget
 from ...models.error_response import ErrorResponse
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     *,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -21,7 +21,7 @@ def _get_kwargs(
 
     params: Dict[str, Any] = {}
 
-    params["identifier"] = identifier
+    params["name"] = name
 
     params = {k: v for k, v in params.items() if v is not UNSET and v is not None}
 
@@ -37,33 +37,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaAgentTarget"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["AgentTarget"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaAgentTarget.from_dict(response_200_item_data)
+            response_200_item = AgentTarget.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -75,7 +75,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaAgentTarget"]]]:
+) -> Response[Union[ErrorResponse, List["AgentTarget"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -87,15 +87,15 @@ def _build_response(
 def sync_detailed(
     *,
     client: AuthenticatedClient,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaAgentTarget"]]]:
+) -> Response[Union[ErrorResponse, List["AgentTarget"]]]:
     """Get all target agents
 
      Gets a list of all configured target agents
 
     Args:
-        identifier (Union[Unset, str]):
+        name (Union[Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -103,11 +103,11 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaAgentTarget']]]
+        Response[Union[ErrorResponse, List['AgentTarget']]]
     """
 
     kwargs = _get_kwargs(
-        identifier=identifier,
+        name=name,
         x_api_key=x_api_key,
     )
 
@@ -121,15 +121,15 @@ def sync_detailed(
 def sync(
     *,
     client: AuthenticatedClient,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaAgentTarget"]]]:
+) -> Optional[Union[ErrorResponse, List["AgentTarget"]]]:
     """Get all target agents
 
      Gets a list of all configured target agents
 
     Args:
-        identifier (Union[Unset, str]):
+        name (Union[Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -137,12 +137,12 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaAgentTarget']]
+        Union[ErrorResponse, List['AgentTarget']]
     """
 
     return sync_detailed(
         client=client,
-        identifier=identifier,
+        name=name,
         x_api_key=x_api_key,
     ).parsed
 
@@ -150,15 +150,15 @@ def sync(
 async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaAgentTarget"]]]:
+) -> Response[Union[ErrorResponse, List["AgentTarget"]]]:
     """Get all target agents
 
      Gets a list of all configured target agents
 
     Args:
-        identifier (Union[Unset, str]):
+        name (Union[Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -166,11 +166,11 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaAgentTarget']]]
+        Response[Union[ErrorResponse, List['AgentTarget']]]
     """
 
     kwargs = _get_kwargs(
-        identifier=identifier,
+        name=name,
         x_api_key=x_api_key,
     )
 
@@ -182,15 +182,15 @@ async def asyncio_detailed(
 async def asyncio(
     *,
     client: AuthenticatedClient,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaAgentTarget"]]]:
+) -> Optional[Union[ErrorResponse, List["AgentTarget"]]]:
     """Get all target agents
 
      Gets a list of all configured target agents
 
     Args:
-        identifier (Union[Unset, str]):
+        name (Union[Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -198,13 +198,13 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaAgentTarget']]
+        Union[ErrorResponse, List['AgentTarget']]
     """
 
     return (
         await asyncio_detailed(
             client=client,
-            identifier=identifier,
+            name=name,
             x_api_key=x_api_key,
         )
     ).parsed
diff --git a/src/maihem/api_client/maihem_client/api/conversations/conversations_get_conversation.py b/src/maihem/api_client/maihem_client/api/conversations/conversations_get_conversation.py
index e09ba7f..610e3bc 100644
--- a/src/maihem/api_client/maihem_client/api/conversations/conversations_get_conversation.py
+++ b/src/maihem/api_client/maihem_client/api/conversations/conversations_get_conversation.py
@@ -31,27 +31,27 @@ def _get_kwargs(
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
 ) -> Optional[Union[ConversationNested, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
+    if response.status_code == 200:
         response_200 = ConversationNested.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
diff --git a/src/maihem/api_client/maihem_client/api/health/health_health.py b/src/maihem/api_client/maihem_client/api/health/health_health.py
index 6dc08cd..39fe124 100644
--- a/src/maihem/api_client/maihem_client/api/health/health_health.py
+++ b/src/maihem/api_client/maihem_client/api/health/health_health.py
@@ -18,7 +18,7 @@ def _get_kwargs() -> Dict[str, Any]:
 
 
 def _parse_response(*, client: Union[AuthenticatedClient, Client], response: httpx.Response) -> Optional[Any]:
-    if response.status_code == HTTPStatus.OK:
+    if response.status_code == 200:
         return None
     if client.raise_on_unexpected_status:
         raise errors.UnexpectedStatus(response.status_code, response.content)
diff --git a/src/maihem/api_client/maihem_client/api/metrics/metrics_get_metric.py b/src/maihem/api_client/maihem_client/api/metrics/metrics_get_metric.py
index ebbed78..f830e55 100644
--- a/src/maihem/api_client/maihem_client/api/metrics/metrics_get_metric.py
+++ b/src/maihem/api_client/maihem_client/api/metrics/metrics_get_metric.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_metric import APISchemaMetric
 from ...models.error_response import ErrorResponse
+from ...models.metric import Metric
 from ...types import UNSET, Response, Unset
 
 
@@ -30,28 +30,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaMetric, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaMetric.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, Metric]]:
+    if response.status_code == 200:
+        response_200 = Metric.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -63,7 +63,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaMetric, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Metric]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -77,7 +77,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaMetric, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Metric]]:
     """Get metric
 
      Get a supported metric
@@ -91,7 +91,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaMetric, ErrorResponse]]
+        Response[Union[ErrorResponse, Metric]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaMetric, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, Metric]]:
     """Get metric
 
      Get a supported metric
@@ -125,7 +125,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaMetric, ErrorResponse]
+        Union[ErrorResponse, Metric]
     """
 
     return sync_detailed(
@@ -140,7 +140,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaMetric, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Metric]]:
     """Get metric
 
      Get a supported metric
@@ -154,7 +154,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaMetric, ErrorResponse]]
+        Response[Union[ErrorResponse, Metric]]
     """
 
     kwargs = _get_kwargs(
@@ -172,7 +172,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaMetric, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, Metric]]:
     """Get metric
 
      Get a supported metric
@@ -186,7 +186,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaMetric, ErrorResponse]
+        Union[ErrorResponse, Metric]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/metrics/metrics_get_metrics.py b/src/maihem/api_client/maihem_client/api/metrics/metrics_get_metrics.py
index b4744e0..7c313cc 100644
--- a/src/maihem/api_client/maihem_client/api/metrics/metrics_get_metrics.py
+++ b/src/maihem/api_client/maihem_client/api/metrics/metrics_get_metrics.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_metric import APISchemaMetric
 from ...models.error_response import ErrorResponse
+from ...models.metric import Metric
 from ...types import UNSET, Response, Unset
 
 
@@ -29,33 +29,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaMetric"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["Metric"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaMetric.from_dict(response_200_item_data)
+            response_200_item = Metric.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -67,7 +67,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaMetric"]]]:
+) -> Response[Union[ErrorResponse, List["Metric"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -80,7 +80,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaMetric"]]]:
+) -> Response[Union[ErrorResponse, List["Metric"]]]:
     """Get metrics
 
      Get all supported metrics
@@ -93,7 +93,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaMetric']]]
+        Response[Union[ErrorResponse, List['Metric']]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaMetric"]]]:
+) -> Optional[Union[ErrorResponse, List["Metric"]]]:
     """Get metrics
 
      Get all supported metrics
@@ -124,7 +124,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaMetric']]
+        Union[ErrorResponse, List['Metric']]
     """
 
     return sync_detailed(
@@ -137,7 +137,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaMetric"]]]:
+) -> Response[Union[ErrorResponse, List["Metric"]]]:
     """Get metrics
 
      Get all supported metrics
@@ -150,7 +150,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaMetric']]]
+        Response[Union[ErrorResponse, List['Metric']]]
     """
 
     kwargs = _get_kwargs(
@@ -166,7 +166,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaMetric"]]]:
+) -> Optional[Union[ErrorResponse, List["Metric"]]]:
     """Get metrics
 
      Get all supported metrics
@@ -179,7 +179,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaMetric']]
+        Union[ErrorResponse, List['Metric']]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/modules/modules_get_module_metrics.py b/src/maihem/api_client/maihem_client/api/modules/modules_get_module_metrics.py
index ac0ad9d..2068787 100644
--- a/src/maihem/api_client/maihem_client/api/modules/modules_get_module_metrics.py
+++ b/src/maihem/api_client/maihem_client/api/modules/modules_get_module_metrics.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_module_metrics import APISchemaModuleMetrics
 from ...models.error_response import ErrorResponse
+from ...models.module_metrics import ModuleMetrics
 from ...types import UNSET, Response, Unset
 
 
@@ -29,33 +29,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaModuleMetrics"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["ModuleMetrics"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaModuleMetrics.from_dict(response_200_item_data)
+            response_200_item = ModuleMetrics.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -67,7 +67,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaModuleMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["ModuleMetrics"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -80,7 +80,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaModuleMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["ModuleMetrics"]]]:
     """Get module metrics
 
      Get all available modules including metrics
@@ -93,7 +93,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaModuleMetrics']]]
+        Response[Union[ErrorResponse, List['ModuleMetrics']]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaModuleMetrics"]]]:
+) -> Optional[Union[ErrorResponse, List["ModuleMetrics"]]]:
     """Get module metrics
 
      Get all available modules including metrics
@@ -124,7 +124,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaModuleMetrics']]
+        Union[ErrorResponse, List['ModuleMetrics']]
     """
 
     return sync_detailed(
@@ -137,7 +137,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaModuleMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["ModuleMetrics"]]]:
     """Get module metrics
 
      Get all available modules including metrics
@@ -150,7 +150,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaModuleMetrics']]]
+        Response[Union[ErrorResponse, List['ModuleMetrics']]]
     """
 
     kwargs = _get_kwargs(
@@ -166,7 +166,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaModuleMetrics"]]]:
+) -> Optional[Union[ErrorResponse, List["ModuleMetrics"]]]:
     """Get module metrics
 
      Get all available modules including metrics
@@ -179,7 +179,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaModuleMetrics']]
+        Union[ErrorResponse, List['ModuleMetrics']]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/modules/modules_get_modules.py b/src/maihem/api_client/maihem_client/api/modules/modules_get_modules.py
index d6eb306..f165a34 100644
--- a/src/maihem/api_client/maihem_client/api/modules/modules_get_modules.py
+++ b/src/maihem/api_client/maihem_client/api/modules/modules_get_modules.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_module import APISchemaModule
 from ...models.error_response import ErrorResponse
+from ...models.module import Module
 from ...types import UNSET, Response, Unset
 
 
@@ -29,33 +29,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaModule"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["Module"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaModule.from_dict(response_200_item_data)
+            response_200_item = Module.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -67,7 +67,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaModule"]]]:
+) -> Response[Union[ErrorResponse, List["Module"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -80,7 +80,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaModule"]]]:
+) -> Response[Union[ErrorResponse, List["Module"]]]:
     """Get modules
 
      Get all available modules
@@ -93,7 +93,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaModule']]]
+        Response[Union[ErrorResponse, List['Module']]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaModule"]]]:
+) -> Optional[Union[ErrorResponse, List["Module"]]]:
     """Get modules
 
      Get all available modules
@@ -124,7 +124,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaModule']]
+        Union[ErrorResponse, List['Module']]
     """
 
     return sync_detailed(
@@ -137,7 +137,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaModule"]]]:
+) -> Response[Union[ErrorResponse, List["Module"]]]:
     """Get modules
 
      Get all available modules
@@ -150,7 +150,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaModule']]]
+        Response[Union[ErrorResponse, List['Module']]]
     """
 
     kwargs = _get_kwargs(
@@ -166,7 +166,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaModule"]]]:
+) -> Optional[Union[ErrorResponse, List["Module"]]]:
     """Get modules
 
      Get all available modules
@@ -179,7 +179,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaModule']]
+        Union[ErrorResponse, List['Module']]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/orgs/orgs_create_org.py b/src/maihem/api_client/maihem_client/api/orgs/orgs_create_org.py
index 7187a8e..f27685f 100644
--- a/src/maihem/api_client/maihem_client/api/orgs/orgs_create_org.py
+++ b/src/maihem/api_client/maihem_client/api/orgs/orgs_create_org.py
@@ -7,13 +7,13 @@
 from ...client import AuthenticatedClient, Client
 from ...models.error_response import ErrorResponse
 from ...models.org import Org
-from ...models.org_base import OrgBase
+from ...models.org_create_request import OrgCreateRequest
 from ...types import Response
 
 
 def _get_kwargs(
     *,
-    body: OrgBase,
+    body: OrgCreateRequest,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
 
@@ -34,27 +34,27 @@ def _get_kwargs(
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
 ) -> Optional[Union[ErrorResponse, Org]]:
-    if response.status_code == HTTPStatus.CREATED:
+    if response.status_code == 201:
         response_201 = Org.from_dict(response.json())
 
         return response_201
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -78,14 +78,14 @@ def _build_response(
 def sync_detailed(
     *,
     client: AuthenticatedClient,
-    body: OrgBase,
+    body: OrgCreateRequest,
 ) -> Response[Union[ErrorResponse, Org]]:
     """Create organization
 
      Create a new organization
 
     Args:
-        body (OrgBase):
+        body (OrgCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@@ -109,14 +109,14 @@ def sync_detailed(
 def sync(
     *,
     client: AuthenticatedClient,
-    body: OrgBase,
+    body: OrgCreateRequest,
 ) -> Optional[Union[ErrorResponse, Org]]:
     """Create organization
 
      Create a new organization
 
     Args:
-        body (OrgBase):
+        body (OrgCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@@ -135,14 +135,14 @@ def sync(
 async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
-    body: OrgBase,
+    body: OrgCreateRequest,
 ) -> Response[Union[ErrorResponse, Org]]:
     """Create organization
 
      Create a new organization
 
     Args:
-        body (OrgBase):
+        body (OrgCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@@ -164,14 +164,14 @@ async def asyncio_detailed(
 async def asyncio(
     *,
     client: AuthenticatedClient,
-    body: OrgBase,
+    body: OrgCreateRequest,
 ) -> Optional[Union[ErrorResponse, Org]]:
     """Create organization
 
      Create a new organization
 
     Args:
-        body (OrgBase):
+        body (OrgCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
diff --git a/src/maihem/api_client/maihem_client/api/users/users_get_user_profile.py b/src/maihem/api_client/maihem_client/api/users/users_get_user_profile.py
index f19007b..0fb5851 100644
--- a/src/maihem/api_client/maihem_client/api/users/users_get_user_profile.py
+++ b/src/maihem/api_client/maihem_client/api/users/users_get_user_profile.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_user_profile import APISchemaUserProfile
 from ...models.error_response import ErrorResponse
+from ...models.user_profile import UserProfile
 from ...types import UNSET, Response, Unset
 
 
@@ -29,28 +29,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaUserProfile, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaUserProfile.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, UserProfile]]:
+    if response.status_code == 200:
+        response_200 = UserProfile.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -62,7 +62,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaUserProfile, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, UserProfile]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -75,7 +75,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaUserProfile, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, UserProfile]]:
     """Get user profile
 
      Get a users profile
@@ -88,7 +88,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaUserProfile, ErrorResponse]]
+        Response[Union[ErrorResponse, UserProfile]]
     """
 
     kwargs = _get_kwargs(
@@ -106,7 +106,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaUserProfile, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, UserProfile]]:
     """Get user profile
 
      Get a users profile
@@ -119,7 +119,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaUserProfile, ErrorResponse]
+        Union[ErrorResponse, UserProfile]
     """
 
     return sync_detailed(
@@ -132,7 +132,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaUserProfile, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, UserProfile]]:
     """Get user profile
 
      Get a users profile
@@ -145,7 +145,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaUserProfile, ErrorResponse]]
+        Response[Union[ErrorResponse, UserProfile]]
     """
 
     kwargs = _get_kwargs(
@@ -161,7 +161,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaUserProfile, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, UserProfile]]:
     """Get user profile
 
      Get a users profile
@@ -174,7 +174,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaUserProfile, ErrorResponse]
+        Union[ErrorResponse, UserProfile]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_org_create.py b/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_org_create.py
index ac4bc53..7769bfd 100644
--- a/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_org_create.py
+++ b/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_org_create.py
@@ -33,10 +33,10 @@ def _get_kwargs(
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
 ) -> Optional[Union[Any, HTTPValidationError]]:
-    if response.status_code == HTTPStatus.CREATED:
+    if response.status_code == 201:
         response_201 = response.json()
         return response_201
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = HTTPValidationError.from_dict(response.json())
 
         return response_422
diff --git a/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_org_user_add.py b/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_org_user_add.py
index defea4f..6932e98 100644
--- a/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_org_user_add.py
+++ b/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_org_user_add.py
@@ -33,10 +33,10 @@ def _get_kwargs(
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
 ) -> Optional[Union[Any, HTTPValidationError]]:
-    if response.status_code == HTTPStatus.OK:
+    if response.status_code == 200:
         response_200 = response.json()
         return response_200
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = HTTPValidationError.from_dict(response.json())
 
         return response_422
diff --git a/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_user_create.py b/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_user_create.py
index e9e646f..451d37c 100644
--- a/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_user_create.py
+++ b/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_user_create.py
@@ -33,10 +33,10 @@ def _get_kwargs(
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
 ) -> Optional[Union[Any, HTTPValidationError]]:
-    if response.status_code == HTTPStatus.CREATED:
+    if response.status_code == 201:
         response_201 = response.json()
         return response_201
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = HTTPValidationError.from_dict(response.json())
 
         return response_422
diff --git a/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_user_update.py b/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_user_update.py
index 49dbdf3..687934a 100644
--- a/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_user_update.py
+++ b/src/maihem/api_client/maihem_client/api/webhooks/webhooks_process_idp_user_update.py
@@ -33,10 +33,10 @@ def _get_kwargs(
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
 ) -> Optional[Union[Any, HTTPValidationError]]:
-    if response.status_code == HTTPStatus.OK:
+    if response.status_code == 200:
         response_200 = response.json()
         return response_200
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = HTTPValidationError.from_dict(response.json())
 
         return response_422
diff --git a/src/maihem/api_client/maihem_client/api/whoami/whoami_who_am_i.py b/src/maihem/api_client/maihem_client/api/whoami/whoami_who_am_i.py
index 3b21520..8c258f7 100644
--- a/src/maihem/api_client/maihem_client/api/whoami/whoami_who_am_i.py
+++ b/src/maihem/api_client/maihem_client/api/whoami/whoami_who_am_i.py
@@ -29,10 +29,10 @@ def _get_kwargs(
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
 ) -> Optional[Union[Any, HTTPValidationError]]:
-    if response.status_code == HTTPStatus.OK:
+    if response.status_code == 200:
         response_200 = response.json()
         return response_200
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = HTTPValidationError.from_dict(response.json())
 
         return response_422
diff --git a/src/maihem/api_client/maihem_client/client.py b/src/maihem/api_client/maihem_client/client.py
index 63a2493..0f6d15e 100644
--- a/src/maihem/api_client/maihem_client/client.py
+++ b/src/maihem/api_client/maihem_client/client.py
@@ -70,7 +70,7 @@ def with_timeout(self, timeout: httpx.Timeout) -> "Client":
         return evolve(self, timeout=timeout)
 
     def set_httpx_client(self, client: httpx.Client) -> "Client":
-        """Manually the underlying httpx.Client
+        """Manually set the underlying httpx.Client
 
         **NOTE**: This will override any other settings on the client, including cookies, headers, and timeout.
         """
@@ -204,7 +204,7 @@ def with_timeout(self, timeout: httpx.Timeout) -> "AuthenticatedClient":
         return evolve(self, timeout=timeout)
 
     def set_httpx_client(self, client: httpx.Client) -> "AuthenticatedClient":
-        """Manually the underlying httpx.Client
+        """Manually set the underlying httpx.Client
 
         **NOTE**: This will override any other settings on the client, including cookies, headers, and timeout.
         """
diff --git a/src/maihem/api_client/maihem_client/models/__init__.py b/src/maihem/api_client/maihem_client/models/__init__.py
index a68120a..cf4122e 100644
--- a/src/maihem/api_client/maihem_client/models/__init__.py
+++ b/src/maihem/api_client/maihem_client/models/__init__.py
@@ -1,54 +1,21 @@
 """Contains all the data models used in inputs/outputs"""
 
-from .agent_maihem_role import AgentMaihemRole
+from .admin_test_result_metric_review_create_request import AdminTestResultMetricReviewCreateRequest
+from .admin_test_result_metric_review_edit_request import AdminTestResultMetricReviewEditRequest
+from .agent_target import AgentTarget
+from .agent_target_create_request import AgentTargetCreateRequest
 from .agent_type import AgentType
-from .api_schema_agent_target import APISchemaAgentTarget
-from .api_schema_agent_target_create_request import APISchemaAgentTargetCreateRequest
-from .api_schema_conversation_turn_create_request import APISchemaConversationTurnCreateRequest
-from .api_schema_conversation_turn_create_request_document_type_0 import (
-    APISchemaConversationTurnCreateRequestDocumentType0,
-)
-from .api_schema_conversation_turn_create_response import APISchemaConversationTurnCreateResponse
-from .api_schema_links import APISchemaLinks
-from .api_schema_metric import APISchemaMetric
-from .api_schema_module import APISchemaModule
-from .api_schema_module_metrics import APISchemaModuleMetrics
-from .api_schema_org import APISchemaOrg
-from .api_schema_test import APISchemaTest
-from .api_schema_test_create_request import APISchemaTestCreateRequest
-from .api_schema_test_create_request_metrics_config import APISchemaTestCreateRequestMetricsConfig
-from .api_schema_test_metrics_config import APISchemaTestMetricsConfig
-from .api_schema_test_result_metric_feedback import APISchemaTestResultMetricFeedback
-from .api_schema_test_result_metric_feedback_create_request import APISchemaTestResultMetricFeedbackCreateRequest
-from .api_schema_test_result_metric_feedback_create_request_feedback import (
-    APISchemaTestResultMetricFeedbackCreateRequestFeedback,
-)
-from .api_schema_test_result_metric_feedback_feedback import APISchemaTestResultMetricFeedbackFeedback
-from .api_schema_test_run import APISchemaTestRun
-from .api_schema_test_run_conversation_scores import APISchemaTestRunConversationScores
-from .api_schema_test_run_conversations import APISchemaTestRunConversations
-from .api_schema_test_run_result_conversations import APISchemaTestRunResultConversations
-from .api_schema_test_run_result_conversations_metric_scores_type_0 import (
-    APISchemaTestRunResultConversationsMetricScoresType0,
-)
-from .api_schema_test_run_result_conversations_metric_summaries_type_0 import (
-    APISchemaTestRunResultConversationsMetricSummariesType0,
-)
-from .api_schema_test_run_result_metric_scores import APISchemaTestRunResultMetricScores
-from .api_schema_test_run_result_metrics import APISchemaTestRunResultMetrics
-from .api_schema_test_run_result_metrics_metric_scores_type_0 import APISchemaTestRunResultMetricsMetricScoresType0
-from .api_schema_test_run_result_metrics_metric_summaries_type_0 import (
-    APISchemaTestRunResultMetricsMetricSummariesType0,
-)
-from .api_schema_test_run_status_update_request import APISchemaTestRunStatusUpdateRequest
-from .api_schema_user import APISchemaUser
-from .api_schema_user_profile import APISchemaUserProfile
 from .conversation_nested import ConversationNested
 from .conversation_nested_evaluation import ConversationNestedEvaluation
 from .conversation_nested_message import ConversationNestedMessage
 from .conversation_nested_sentence import ConversationNestedSentence
-from .conversation_nested_token_cost import ConversationNestedTokenCost
+from .conversation_nested_token_cost_base import ConversationNestedTokenCostBase
 from .conversation_nested_turn import ConversationNestedTurn
+from .conversation_turn_create_request import ConversationTurnCreateRequest
+from .conversation_turn_create_response import ConversationTurnCreateResponse
+from .create_test_run_request import CreateTestRunRequest
+from .criteria import Criteria
+from .criteria_instance_base import CriteriaInstanceBase
 from .error_codes import ErrorCodes
 from .error_response import ErrorResponse
 from .error_response_error import ErrorResponseError
@@ -57,52 +24,61 @@
 from .idp_org_user_add_request import IDPOrgUserAddRequest
 from .idp_user_create_request import IDPUserCreateRequest
 from .idp_user_update_request import IDPUserUpdateRequest
+from .links import Links
+from .metric import Metric
+from .module import Module
+from .module_metrics import ModuleMetrics
 from .org import Org
-from .org_base import OrgBase
+from .org_create_request import OrgCreateRequest
+from .test import Test
+from .test_create_request import TestCreateRequest
+from .test_create_request_documents_type_0 import TestCreateRequestDocumentsType0
+from .test_create_request_metrics_config import TestCreateRequestMetricsConfig
+from .test_documents_type_0 import TestDocumentsType0
+from .test_metrics_config import TestMetricsConfig
 from .test_result_enum import TestResultEnum
+from .test_result_metric_feedback import TestResultMetricFeedback
+from .test_result_metric_feedback_create_request import TestResultMetricFeedbackCreateRequest
+from .test_result_metric_feedback_create_request_feedback import TestResultMetricFeedbackCreateRequestFeedback
+from .test_result_metric_feedback_feedback import TestResultMetricFeedbackFeedback
+from .test_run import TestRun
+from .test_run_conversation_i_ds import TestRunConversationIDs
+from .test_run_conversation_scores import TestRunConversationScores
+from .test_run_metric_scores import TestRunMetricScores
+from .test_run_metric_scores_criteria_failures_type_0 import TestRunMetricScoresCriteriaFailuresType0
+from .test_run_results import TestRunResults
+from .test_run_results_conversations import TestRunResultsConversations
+from .test_run_results_conversations_metric_scores_type_0 import TestRunResultsConversationsMetricScoresType0
+from .test_run_results_conversations_module_group_scores_type_0 import TestRunResultsConversationsModuleGroupScoresType0
+from .test_run_results_conversations_module_scores_type_0 import TestRunResultsConversationsModuleScoresType0
+from .test_run_results_metric_scores_type_0 import TestRunResultsMetricScoresType0
+from .test_run_results_module_group_scores_type_0 import TestRunResultsModuleGroupScoresType0
+from .test_run_results_module_scores_type_0 import TestRunResultsModuleScoresType0
+from .test_run_status_update_request import TestRunStatusUpdateRequest
 from .test_status_enum import TestStatusEnum
+from .user import User
+from .user_profile import UserProfile
+from .v_test_result_metric_review_audit import VTestResultMetricReviewAudit
+from .v_test_result_metric_review_state import VTestResultMetricReviewState
 from .validation_error import ValidationError
 
 __all__ = (
-    "AgentMaihemRole",
+    "AdminTestResultMetricReviewCreateRequest",
+    "AdminTestResultMetricReviewEditRequest",
+    "AgentTarget",
+    "AgentTargetCreateRequest",
     "AgentType",
-    "APISchemaAgentTarget",
-    "APISchemaAgentTargetCreateRequest",
-    "APISchemaConversationTurnCreateRequest",
-    "APISchemaConversationTurnCreateRequestDocumentType0",
-    "APISchemaConversationTurnCreateResponse",
-    "APISchemaLinks",
-    "APISchemaMetric",
-    "APISchemaModule",
-    "APISchemaModuleMetrics",
-    "APISchemaOrg",
-    "APISchemaTest",
-    "APISchemaTestCreateRequest",
-    "APISchemaTestCreateRequestMetricsConfig",
-    "APISchemaTestMetricsConfig",
-    "APISchemaTestResultMetricFeedback",
-    "APISchemaTestResultMetricFeedbackCreateRequest",
-    "APISchemaTestResultMetricFeedbackCreateRequestFeedback",
-    "APISchemaTestResultMetricFeedbackFeedback",
-    "APISchemaTestRun",
-    "APISchemaTestRunConversations",
-    "APISchemaTestRunConversationScores",
-    "APISchemaTestRunResultConversations",
-    "APISchemaTestRunResultConversationsMetricScoresType0",
-    "APISchemaTestRunResultConversationsMetricSummariesType0",
-    "APISchemaTestRunResultMetrics",
-    "APISchemaTestRunResultMetricScores",
-    "APISchemaTestRunResultMetricsMetricScoresType0",
-    "APISchemaTestRunResultMetricsMetricSummariesType0",
-    "APISchemaTestRunStatusUpdateRequest",
-    "APISchemaUser",
-    "APISchemaUserProfile",
     "ConversationNested",
     "ConversationNestedEvaluation",
     "ConversationNestedMessage",
     "ConversationNestedSentence",
-    "ConversationNestedTokenCost",
+    "ConversationNestedTokenCostBase",
     "ConversationNestedTurn",
+    "ConversationTurnCreateRequest",
+    "ConversationTurnCreateResponse",
+    "CreateTestRunRequest",
+    "Criteria",
+    "CriteriaInstanceBase",
     "ErrorCodes",
     "ErrorResponse",
     "ErrorResponseError",
@@ -111,9 +87,41 @@
     "IDPOrgUserAddRequest",
     "IDPUserCreateRequest",
     "IDPUserUpdateRequest",
+    "Links",
+    "Metric",
+    "Module",
+    "ModuleMetrics",
     "Org",
-    "OrgBase",
+    "OrgCreateRequest",
+    "Test",
+    "TestCreateRequest",
+    "TestCreateRequestDocumentsType0",
+    "TestCreateRequestMetricsConfig",
+    "TestDocumentsType0",
+    "TestMetricsConfig",
     "TestResultEnum",
+    "TestResultMetricFeedback",
+    "TestResultMetricFeedbackCreateRequest",
+    "TestResultMetricFeedbackCreateRequestFeedback",
+    "TestResultMetricFeedbackFeedback",
+    "TestRun",
+    "TestRunConversationIDs",
+    "TestRunConversationScores",
+    "TestRunMetricScores",
+    "TestRunMetricScoresCriteriaFailuresType0",
+    "TestRunResults",
+    "TestRunResultsConversations",
+    "TestRunResultsConversationsMetricScoresType0",
+    "TestRunResultsConversationsModuleGroupScoresType0",
+    "TestRunResultsConversationsModuleScoresType0",
+    "TestRunResultsMetricScoresType0",
+    "TestRunResultsModuleGroupScoresType0",
+    "TestRunResultsModuleScoresType0",
+    "TestRunStatusUpdateRequest",
     "TestStatusEnum",
+    "User",
+    "UserProfile",
     "ValidationError",
+    "VTestResultMetricReviewAudit",
+    "VTestResultMetricReviewState",
 )
diff --git a/src/maihem/api_client/maihem_client/models/agent_maihem_role.py b/src/maihem/api_client/maihem_client/models/agent_maihem_role.py
deleted file mode 100644
index d08ca1e..0000000
--- a/src/maihem/api_client/maihem_client/models/agent_maihem_role.py
+++ /dev/null
@@ -1,10 +0,0 @@
-from enum import Enum
-
-
-class AgentMaihemRole(str, Enum):
-    QA = "qa"
-    SAFETY = "safety"
-    SEC = "sec"
-
-    def __str__(self) -> str:
-        return str(self.value)
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_agent_target.py b/src/maihem/api_client/maihem_client/models/agent_target.py
similarity index 66%
rename from src/maihem/api_client/maihem_client/models/api_schema_agent_target.py
rename to src/maihem/api_client/maihem_client/models/agent_target.py
index e55962c..70c8daf 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_agent_target.py
+++ b/src/maihem/api_client/maihem_client/models/agent_target.py
@@ -9,43 +9,47 @@
 from ..models.test_status_enum import TestStatusEnum
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="APISchemaAgentTarget")
+T = TypeVar("T", bound="AgentTarget")
 
 
 @_attrs_define
-class APISchemaAgentTarget:
+class AgentTarget:
     """
     Attributes:
         id (str):
         created_at (datetime.datetime):
         updated_at (datetime.datetime):
-        identifier (str):
+        name (str):
         role (str):
         language (str):
-        name (Union[None, Unset, str]):
+        label (Union[None, Unset, str]):
         description (Union[None, Unset, str]):
         industry (Union[None, Unset, str]):
         url (Union[None, Unset, str]):
         last_test_run_id (Union[None, Unset, str]):
-        last_test_run_at (Union[None, Unset, datetime.datetime]):
+        last_test_run_started_at (Union[None, Unset, datetime.datetime]):
+        last_test_run_completed_at (Union[None, Unset, datetime.datetime]):
         last_test_run_status (Union[None, TestStatusEnum, Unset]):
         last_test_run_result (Union[None, TestResultEnum, Unset]):
+        last_test_run_result_score (Union[None, Unset, float]):
     """
 
     id: str
     created_at: datetime.datetime
     updated_at: datetime.datetime
-    identifier: str
+    name: str
     role: str
     language: str
-    name: Union[None, Unset, str] = UNSET
+    label: Union[None, Unset, str] = UNSET
     description: Union[None, Unset, str] = UNSET
     industry: Union[None, Unset, str] = UNSET
     url: Union[None, Unset, str] = UNSET
     last_test_run_id: Union[None, Unset, str] = UNSET
-    last_test_run_at: Union[None, Unset, datetime.datetime] = UNSET
+    last_test_run_started_at: Union[None, Unset, datetime.datetime] = UNSET
+    last_test_run_completed_at: Union[None, Unset, datetime.datetime] = UNSET
     last_test_run_status: Union[None, TestStatusEnum, Unset] = UNSET
     last_test_run_result: Union[None, TestResultEnum, Unset] = UNSET
+    last_test_run_result_score: Union[None, Unset, float] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
@@ -55,17 +59,17 @@ def to_dict(self) -> Dict[str, Any]:
 
         updated_at = self.updated_at.isoformat()
 
-        identifier = self.identifier
+        name = self.name
 
         role = self.role
 
         language = self.language
 
-        name: Union[None, Unset, str]
-        if isinstance(self.name, Unset):
-            name = UNSET
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
         else:
-            name = self.name
+            label = self.label
 
         description: Union[None, Unset, str]
         if isinstance(self.description, Unset):
@@ -91,13 +95,21 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             last_test_run_id = self.last_test_run_id
 
-        last_test_run_at: Union[None, Unset, str]
-        if isinstance(self.last_test_run_at, Unset):
-            last_test_run_at = UNSET
-        elif isinstance(self.last_test_run_at, datetime.datetime):
-            last_test_run_at = self.last_test_run_at.isoformat()
+        last_test_run_started_at: Union[None, Unset, str]
+        if isinstance(self.last_test_run_started_at, Unset):
+            last_test_run_started_at = UNSET
+        elif isinstance(self.last_test_run_started_at, datetime.datetime):
+            last_test_run_started_at = self.last_test_run_started_at.isoformat()
         else:
-            last_test_run_at = self.last_test_run_at
+            last_test_run_started_at = self.last_test_run_started_at
+
+        last_test_run_completed_at: Union[None, Unset, str]
+        if isinstance(self.last_test_run_completed_at, Unset):
+            last_test_run_completed_at = UNSET
+        elif isinstance(self.last_test_run_completed_at, datetime.datetime):
+            last_test_run_completed_at = self.last_test_run_completed_at.isoformat()
+        else:
+            last_test_run_completed_at = self.last_test_run_completed_at
 
         last_test_run_status: Union[None, Unset, str]
         if isinstance(self.last_test_run_status, Unset):
@@ -115,6 +127,12 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             last_test_run_result = self.last_test_run_result
 
+        last_test_run_result_score: Union[None, Unset, float]
+        if isinstance(self.last_test_run_result_score, Unset):
+            last_test_run_result_score = UNSET
+        else:
+            last_test_run_result_score = self.last_test_run_result_score
+
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
         field_dict.update(
@@ -122,13 +140,13 @@ def to_dict(self) -> Dict[str, Any]:
                 "id": id,
                 "created_at": created_at,
                 "updated_at": updated_at,
-                "identifier": identifier,
+                "name": name,
                 "role": role,
                 "language": language,
             }
         )
-        if name is not UNSET:
-            field_dict["name"] = name
+        if label is not UNSET:
+            field_dict["label"] = label
         if description is not UNSET:
             field_dict["description"] = description
         if industry is not UNSET:
@@ -137,12 +155,16 @@ def to_dict(self) -> Dict[str, Any]:
             field_dict["url"] = url
         if last_test_run_id is not UNSET:
             field_dict["last_test_run_id"] = last_test_run_id
-        if last_test_run_at is not UNSET:
-            field_dict["last_test_run_at"] = last_test_run_at
+        if last_test_run_started_at is not UNSET:
+            field_dict["last_test_run_started_at"] = last_test_run_started_at
+        if last_test_run_completed_at is not UNSET:
+            field_dict["last_test_run_completed_at"] = last_test_run_completed_at
         if last_test_run_status is not UNSET:
             field_dict["last_test_run_status"] = last_test_run_status
         if last_test_run_result is not UNSET:
             field_dict["last_test_run_result"] = last_test_run_result
+        if last_test_run_result_score is not UNSET:
+            field_dict["last_test_run_result_score"] = last_test_run_result_score
 
         return field_dict
 
@@ -155,20 +177,20 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         updated_at = isoparse(d.pop("updated_at"))
 
-        identifier = d.pop("identifier")
+        name = d.pop("name")
 
         role = d.pop("role")
 
         language = d.pop("language")
 
-        def _parse_name(data: object) -> Union[None, Unset, str]:
+        def _parse_label(data: object) -> Union[None, Unset, str]:
             if data is None:
                 return data
             if isinstance(data, Unset):
                 return data
             return cast(Union[None, Unset, str], data)
 
-        name = _parse_name(d.pop("name", UNSET))
+        label = _parse_label(d.pop("label", UNSET))
 
         def _parse_description(data: object) -> Union[None, Unset, str]:
             if data is None:
@@ -206,7 +228,7 @@ def _parse_last_test_run_id(data: object) -> Union[None, Unset, str]:
 
         last_test_run_id = _parse_last_test_run_id(d.pop("last_test_run_id", UNSET))
 
-        def _parse_last_test_run_at(data: object) -> Union[None, Unset, datetime.datetime]:
+        def _parse_last_test_run_started_at(data: object) -> Union[None, Unset, datetime.datetime]:
             if data is None:
                 return data
             if isinstance(data, Unset):
@@ -214,14 +236,31 @@ def _parse_last_test_run_at(data: object) -> Union[None, Unset, datetime.datetim
             try:
                 if not isinstance(data, str):
                     raise TypeError()
-                last_test_run_at_type_0 = isoparse(data)
+                last_test_run_started_at_type_0 = isoparse(data)
 
-                return last_test_run_at_type_0
+                return last_test_run_started_at_type_0
             except:  # noqa: E722
                 pass
             return cast(Union[None, Unset, datetime.datetime], data)
 
-        last_test_run_at = _parse_last_test_run_at(d.pop("last_test_run_at", UNSET))
+        last_test_run_started_at = _parse_last_test_run_started_at(d.pop("last_test_run_started_at", UNSET))
+
+        def _parse_last_test_run_completed_at(data: object) -> Union[None, Unset, datetime.datetime]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, str):
+                    raise TypeError()
+                last_test_run_completed_at_type_0 = isoparse(data)
+
+                return last_test_run_completed_at_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union[None, Unset, datetime.datetime], data)
+
+        last_test_run_completed_at = _parse_last_test_run_completed_at(d.pop("last_test_run_completed_at", UNSET))
 
         def _parse_last_test_run_status(data: object) -> Union[None, TestStatusEnum, Unset]:
             if data is None:
@@ -257,25 +296,36 @@ def _parse_last_test_run_result(data: object) -> Union[None, TestResultEnum, Uns
 
         last_test_run_result = _parse_last_test_run_result(d.pop("last_test_run_result", UNSET))
 
-        api_schema_agent_target = cls(
+        def _parse_last_test_run_result_score(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        last_test_run_result_score = _parse_last_test_run_result_score(d.pop("last_test_run_result_score", UNSET))
+
+        agent_target = cls(
             id=id,
             created_at=created_at,
             updated_at=updated_at,
-            identifier=identifier,
+            name=name,
             role=role,
             language=language,
-            name=name,
+            label=label,
             description=description,
             industry=industry,
             url=url,
             last_test_run_id=last_test_run_id,
-            last_test_run_at=last_test_run_at,
+            last_test_run_started_at=last_test_run_started_at,
+            last_test_run_completed_at=last_test_run_completed_at,
             last_test_run_status=last_test_run_status,
             last_test_run_result=last_test_run_result,
+            last_test_run_result_score=last_test_run_result_score,
         )
 
-        api_schema_agent_target.additional_properties = d
-        return api_schema_agent_target
+        agent_target.additional_properties = d
+        return agent_target
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_agent_target_create_request.py b/src/maihem/api_client/maihem_client/models/agent_target_create_request.py
similarity index 82%
rename from src/maihem/api_client/maihem_client/models/api_schema_agent_target_create_request.py
rename to src/maihem/api_client/maihem_client/models/agent_target_create_request.py
index 3f9a475..510da60 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_agent_target_create_request.py
+++ b/src/maihem/api_client/maihem_client/models/agent_target_create_request.py
@@ -5,25 +5,25 @@
 
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="APISchemaAgentTargetCreateRequest")
+T = TypeVar("T", bound="AgentTargetCreateRequest")
 
 
 @_attrs_define
-class APISchemaAgentTargetCreateRequest:
+class AgentTargetCreateRequest:
     """
     Attributes:
-        identifier (str):
+        name (str):
         role (str):
-        name (Union[None, Unset, str]):
+        label (Union[None, Unset, str]):
         description (Union[None, Unset, str]):
         industry (Union[None, Unset, str]):
         language (Union[None, Unset, str]):  Default: 'en'.
         url (Union[None, Unset, str]):
     """
 
-    identifier: str
+    name: str
     role: str
-    name: Union[None, Unset, str] = UNSET
+    label: Union[None, Unset, str] = UNSET
     description: Union[None, Unset, str] = UNSET
     industry: Union[None, Unset, str] = UNSET
     language: Union[None, Unset, str] = "en"
@@ -31,15 +31,15 @@ class APISchemaAgentTargetCreateRequest:
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
-        identifier = self.identifier
+        name = self.name
 
         role = self.role
 
-        name: Union[None, Unset, str]
-        if isinstance(self.name, Unset):
-            name = UNSET
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
         else:
-            name = self.name
+            label = self.label
 
         description: Union[None, Unset, str]
         if isinstance(self.description, Unset):
@@ -69,12 +69,12 @@ def to_dict(self) -> Dict[str, Any]:
         field_dict.update(self.additional_properties)
         field_dict.update(
             {
-                "identifier": identifier,
+                "name": name,
                 "role": role,
             }
         )
-        if name is not UNSET:
-            field_dict["name"] = name
+        if label is not UNSET:
+            field_dict["label"] = label
         if description is not UNSET:
             field_dict["description"] = description
         if industry is not UNSET:
@@ -89,18 +89,18 @@ def to_dict(self) -> Dict[str, Any]:
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
-        identifier = d.pop("identifier")
+        name = d.pop("name")
 
         role = d.pop("role")
 
-        def _parse_name(data: object) -> Union[None, Unset, str]:
+        def _parse_label(data: object) -> Union[None, Unset, str]:
             if data is None:
                 return data
             if isinstance(data, Unset):
                 return data
             return cast(Union[None, Unset, str], data)
 
-        name = _parse_name(d.pop("name", UNSET))
+        label = _parse_label(d.pop("label", UNSET))
 
         def _parse_description(data: object) -> Union[None, Unset, str]:
             if data is None:
@@ -138,18 +138,18 @@ def _parse_url(data: object) -> Union[None, Unset, str]:
 
         url = _parse_url(d.pop("url", UNSET))
 
-        api_schema_agent_target_create_request = cls(
-            identifier=identifier,
-            role=role,
+        agent_target_create_request = cls(
             name=name,
+            role=role,
+            label=label,
             description=description,
             industry=industry,
             language=language,
             url=url,
         )
 
-        api_schema_agent_target_create_request.additional_properties = d
-        return api_schema_agent_target_create_request
+        agent_target_create_request.additional_properties = d
+        return agent_target_create_request
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_org.py b/src/maihem/api_client/maihem_client/models/api_schema_org.py
deleted file mode 100644
index b17bcab..0000000
--- a/src/maihem/api_client/maihem_client/models/api_schema_org.py
+++ /dev/null
@@ -1,106 +0,0 @@
-import datetime
-from typing import Any, Dict, List, Type, TypeVar, Union, cast
-
-from attrs import define as _attrs_define
-from attrs import field as _attrs_field
-from dateutil.parser import isoparse
-
-from ..types import UNSET, Unset
-
-T = TypeVar("T", bound="APISchemaOrg")
-
-
-@_attrs_define
-class APISchemaOrg:
-    """
-    Attributes:
-        id (str):
-        created_at (datetime.datetime):
-        updated_at (datetime.datetime):
-        name (str):
-        idp_org_id (Union[None, Unset, str]):
-    """
-
-    id: str
-    created_at: datetime.datetime
-    updated_at: datetime.datetime
-    name: str
-    idp_org_id: Union[None, Unset, str] = UNSET
-    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
-
-    def to_dict(self) -> Dict[str, Any]:
-        id = self.id
-
-        created_at = self.created_at.isoformat()
-
-        updated_at = self.updated_at.isoformat()
-
-        name = self.name
-
-        idp_org_id: Union[None, Unset, str]
-        if isinstance(self.idp_org_id, Unset):
-            idp_org_id = UNSET
-        else:
-            idp_org_id = self.idp_org_id
-
-        field_dict: Dict[str, Any] = {}
-        field_dict.update(self.additional_properties)
-        field_dict.update(
-            {
-                "id": id,
-                "created_at": created_at,
-                "updated_at": updated_at,
-                "name": name,
-            }
-        )
-        if idp_org_id is not UNSET:
-            field_dict["idp_org_id"] = idp_org_id
-
-        return field_dict
-
-    @classmethod
-    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        d = src_dict.copy()
-        id = d.pop("id")
-
-        created_at = isoparse(d.pop("created_at"))
-
-        updated_at = isoparse(d.pop("updated_at"))
-
-        name = d.pop("name")
-
-        def _parse_idp_org_id(data: object) -> Union[None, Unset, str]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            return cast(Union[None, Unset, str], data)
-
-        idp_org_id = _parse_idp_org_id(d.pop("idp_org_id", UNSET))
-
-        api_schema_org = cls(
-            id=id,
-            created_at=created_at,
-            updated_at=updated_at,
-            name=name,
-            idp_org_id=idp_org_id,
-        )
-
-        api_schema_org.additional_properties = d
-        return api_schema_org
-
-    @property
-    def additional_keys(self) -> List[str]:
-        return list(self.additional_properties.keys())
-
-    def __getitem__(self, key: str) -> Any:
-        return self.additional_properties[key]
-
-    def __setitem__(self, key: str, value: Any) -> None:
-        self.additional_properties[key] = value
-
-    def __delitem__(self, key: str) -> None:
-        del self.additional_properties[key]
-
-    def __contains__(self, key: str) -> bool:
-        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/conversation_nested.py b/src/maihem/api_client/maihem_client/models/conversation_nested.py
index 0aa2827..57914bf 100644
--- a/src/maihem/api_client/maihem_client/models/conversation_nested.py
+++ b/src/maihem/api_client/maihem_client/models/conversation_nested.py
@@ -30,6 +30,7 @@ class ConversationNested:
         result (Union[None, TestResultEnum, Unset]):
         evaluations (Union[Unset, List['ConversationNestedEvaluation']]):
         conversation_turns (Union[Unset, List['ConversationNestedTurn']]):
+        result_score (Union[None, Unset, float]):
     """
 
     id: str
@@ -41,6 +42,7 @@ class ConversationNested:
     result: Union[None, TestResultEnum, Unset] = UNSET
     evaluations: Union[Unset, List["ConversationNestedEvaluation"]] = UNSET
     conversation_turns: Union[Unset, List["ConversationNestedTurn"]] = UNSET
+    result_score: Union[None, Unset, float] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
@@ -90,6 +92,12 @@ def to_dict(self) -> Dict[str, Any]:
                 conversation_turns_item = conversation_turns_item_data.to_dict()
                 conversation_turns.append(conversation_turns_item)
 
+        result_score: Union[None, Unset, float]
+        if isinstance(self.result_score, Unset):
+            result_score = UNSET
+        else:
+            result_score = self.result_score
+
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
         field_dict.update(
@@ -110,6 +118,8 @@ def to_dict(self) -> Dict[str, Any]:
             field_dict["evaluations"] = evaluations
         if conversation_turns is not UNSET:
             field_dict["conversation_turns"] = conversation_turns
+        if result_score is not UNSET:
+            field_dict["result_score"] = result_score
 
         return field_dict
 
@@ -192,6 +202,15 @@ def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
 
             conversation_turns.append(conversation_turns_item)
 
+        def _parse_result_score(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        result_score = _parse_result_score(d.pop("result_score", UNSET))
+
         conversation_nested = cls(
             id=id,
             created_at=created_at,
@@ -202,6 +221,7 @@ def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
             result=result,
             evaluations=evaluations,
             conversation_turns=conversation_turns,
+            result_score=result_score,
         )
 
         conversation_nested.additional_properties = d
diff --git a/src/maihem/api_client/maihem_client/models/conversation_nested_evaluation.py b/src/maihem/api_client/maihem_client/models/conversation_nested_evaluation.py
index a8e8faa..dcb127b 100644
--- a/src/maihem/api_client/maihem_client/models/conversation_nested_evaluation.py
+++ b/src/maihem/api_client/maihem_client/models/conversation_nested_evaluation.py
@@ -7,7 +7,7 @@
 from ..types import UNSET, Unset
 
 if TYPE_CHECKING:
-    from ..models.conversation_nested_token_cost import ConversationNestedTokenCost
+    from ..models.conversation_nested_token_cost_base import ConversationNestedTokenCostBase
 
 
 T = TypeVar("T", bound="ConversationNestedEvaluation")
@@ -18,32 +18,32 @@ class ConversationNestedEvaluation:
     """
     Attributes:
         id (str):
-        metric_slug (str):
         score (Union[None, Unset, float]):
         result (Union[None, TestResultEnum, Unset]):
+        metric_slug (Union[None, Unset, str]):
+        criteria (Union[None, Unset, str]):
         confidence (Union[None, Unset, float]):
         explanation (Union[None, Unset, str]):
         classification (Union[None, Unset, str]):
-        token_cost (Union['ConversationNestedTokenCost', None, Unset]):
+        token_cost (Union['ConversationNestedTokenCostBase', None, Unset]):
     """
 
     id: str
-    metric_slug: str
     score: Union[None, Unset, float] = UNSET
     result: Union[None, TestResultEnum, Unset] = UNSET
+    metric_slug: Union[None, Unset, str] = UNSET
+    criteria: Union[None, Unset, str] = UNSET
     confidence: Union[None, Unset, float] = UNSET
     explanation: Union[None, Unset, str] = UNSET
     classification: Union[None, Unset, str] = UNSET
-    token_cost: Union["ConversationNestedTokenCost", None, Unset] = UNSET
+    token_cost: Union["ConversationNestedTokenCostBase", None, Unset] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
-        from ..models.conversation_nested_token_cost import ConversationNestedTokenCost
+        from ..models.conversation_nested_token_cost_base import ConversationNestedTokenCostBase
 
         id = self.id
 
-        metric_slug = self.metric_slug
-
         score: Union[None, Unset, float]
         if isinstance(self.score, Unset):
             score = UNSET
@@ -58,6 +58,18 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             result = self.result
 
+        metric_slug: Union[None, Unset, str]
+        if isinstance(self.metric_slug, Unset):
+            metric_slug = UNSET
+        else:
+            metric_slug = self.metric_slug
+
+        criteria: Union[None, Unset, str]
+        if isinstance(self.criteria, Unset):
+            criteria = UNSET
+        else:
+            criteria = self.criteria
+
         confidence: Union[None, Unset, float]
         if isinstance(self.confidence, Unset):
             confidence = UNSET
@@ -79,7 +91,7 @@ def to_dict(self) -> Dict[str, Any]:
         token_cost: Union[Dict[str, Any], None, Unset]
         if isinstance(self.token_cost, Unset):
             token_cost = UNSET
-        elif isinstance(self.token_cost, ConversationNestedTokenCost):
+        elif isinstance(self.token_cost, ConversationNestedTokenCostBase):
             token_cost = self.token_cost.to_dict()
         else:
             token_cost = self.token_cost
@@ -89,13 +101,16 @@ def to_dict(self) -> Dict[str, Any]:
         field_dict.update(
             {
                 "id": id,
-                "metric_slug": metric_slug,
             }
         )
         if score is not UNSET:
             field_dict["score"] = score
         if result is not UNSET:
             field_dict["result"] = result
+        if metric_slug is not UNSET:
+            field_dict["metric_slug"] = metric_slug
+        if criteria is not UNSET:
+            field_dict["criteria"] = criteria
         if confidence is not UNSET:
             field_dict["confidence"] = confidence
         if explanation is not UNSET:
@@ -109,13 +124,11 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.conversation_nested_token_cost import ConversationNestedTokenCost
+        from ..models.conversation_nested_token_cost_base import ConversationNestedTokenCostBase
 
         d = src_dict.copy()
         id = d.pop("id")
 
-        metric_slug = d.pop("metric_slug")
-
         def _parse_score(data: object) -> Union[None, Unset, float]:
             if data is None:
                 return data
@@ -142,6 +155,24 @@ def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
 
         result = _parse_result(d.pop("result", UNSET))
 
+        def _parse_metric_slug(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        metric_slug = _parse_metric_slug(d.pop("metric_slug", UNSET))
+
+        def _parse_criteria(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        criteria = _parse_criteria(d.pop("criteria", UNSET))
+
         def _parse_confidence(data: object) -> Union[None, Unset, float]:
             if data is None:
                 return data
@@ -169,9 +200,7 @@ def _parse_classification(data: object) -> Union[None, Unset, str]:
 
         classification = _parse_classification(d.pop("classification", UNSET))
 
-        def _parse_token_cost(
-            data: object,
-        ) -> Union["ConversationNestedTokenCost", None, Unset]:
+        def _parse_token_cost(data: object) -> Union["ConversationNestedTokenCostBase", None, Unset]:
             if data is None:
                 return data
             if isinstance(data, Unset):
@@ -179,20 +208,21 @@ def _parse_token_cost(
             try:
                 if not isinstance(data, dict):
                     raise TypeError()
-                token_cost_type_0 = ConversationNestedTokenCost.from_dict(data)
+                token_cost_type_0 = ConversationNestedTokenCostBase.from_dict(data)
 
                 return token_cost_type_0
             except:  # noqa: E722
                 pass
-            return cast(Union["ConversationNestedTokenCost", None, Unset], data)
+            return cast(Union["ConversationNestedTokenCostBase", None, Unset], data)
 
         token_cost = _parse_token_cost(d.pop("token_cost", UNSET))
 
         conversation_nested_evaluation = cls(
             id=id,
-            metric_slug=metric_slug,
             score=score,
             result=result,
+            metric_slug=metric_slug,
+            criteria=criteria,
             confidence=confidence,
             explanation=explanation,
             classification=classification,
diff --git a/src/maihem/api_client/maihem_client/models/conversation_nested_token_cost.py b/src/maihem/api_client/maihem_client/models/conversation_nested_token_cost_base.py
similarity index 68%
rename from src/maihem/api_client/maihem_client/models/conversation_nested_token_cost.py
rename to src/maihem/api_client/maihem_client/models/conversation_nested_token_cost_base.py
index 27ee59b..03202e5 100644
--- a/src/maihem/api_client/maihem_client/models/conversation_nested_token_cost.py
+++ b/src/maihem/api_client/maihem_client/models/conversation_nested_token_cost_base.py
@@ -1,32 +1,32 @@
-from typing import Any, Dict, List, Type, TypeVar
+from typing import Any, Dict, List, Type, TypeVar, Union, cast
 
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
-T = TypeVar("T", bound="ConversationNestedTokenCost")
+from ..types import UNSET, Unset
+
+T = TypeVar("T", bound="ConversationNestedTokenCostBase")
 
 
 @_attrs_define
-class ConversationNestedTokenCost:
+class ConversationNestedTokenCostBase:
     """
     Attributes:
-        id (str):
         input_tokens (int):
         output_tokens (int):
         cost_amount (int):
         cost_currency (str):
+        id (Union[None, Unset, str]):
     """
 
-    id: str
     input_tokens: int
     output_tokens: int
     cost_amount: int
     cost_currency: str
+    id: Union[None, Unset, str] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
-        id = self.id
-
         input_tokens = self.input_tokens
 
         output_tokens = self.output_tokens
@@ -35,25 +35,30 @@ def to_dict(self) -> Dict[str, Any]:
 
         cost_currency = self.cost_currency
 
+        id: Union[None, Unset, str]
+        if isinstance(self.id, Unset):
+            id = UNSET
+        else:
+            id = self.id
+
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
         field_dict.update(
             {
-                "id": id,
                 "input_tokens": input_tokens,
                 "output_tokens": output_tokens,
                 "cost_amount": cost_amount,
                 "cost_currency": cost_currency,
             }
         )
+        if id is not UNSET:
+            field_dict["id"] = id
 
         return field_dict
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
-        id = d.pop("id")
-
         input_tokens = d.pop("input_tokens")
 
         output_tokens = d.pop("output_tokens")
@@ -62,16 +67,25 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         cost_currency = d.pop("cost_currency")
 
-        conversation_nested_token_cost = cls(
-            id=id,
+        def _parse_id(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        id = _parse_id(d.pop("id", UNSET))
+
+        conversation_nested_token_cost_base = cls(
             input_tokens=input_tokens,
             output_tokens=output_tokens,
             cost_amount=cost_amount,
             cost_currency=cost_currency,
+            id=id,
         )
 
-        conversation_nested_token_cost.additional_properties = d
-        return conversation_nested_token_cost
+        conversation_nested_token_cost_base.additional_properties = d
+        return conversation_nested_token_cost_base
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_request.py b/src/maihem/api_client/maihem_client/models/conversation_turn_create_request.py
similarity index 55%
rename from src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_request.py
rename to src/maihem/api_client/maihem_client/models/conversation_turn_create_request.py
index e930ec6..0c71010 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_request.py
+++ b/src/maihem/api_client/maihem_client/models/conversation_turn_create_request.py
@@ -1,38 +1,26 @@
-from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar, Union, cast
+from typing import Any, Dict, List, Type, TypeVar, Union, cast
 
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
 from ..types import UNSET, Unset
 
-if TYPE_CHECKING:
-    from ..models.api_schema_conversation_turn_create_request_document_type_0 import (
-        APISchemaConversationTurnCreateRequestDocumentType0,
-    )
-
-
-T = TypeVar("T", bound="APISchemaConversationTurnCreateRequest")
+T = TypeVar("T", bound="ConversationTurnCreateRequest")
 
 
 @_attrs_define
-class APISchemaConversationTurnCreateRequest:
+class ConversationTurnCreateRequest:
     """
     Attributes:
         message (Union[None, Unset, str]):
         contexts (Union[List[str], None, Unset]):
-        document (Union['APISchemaConversationTurnCreateRequestDocumentType0', None, Unset]):
     """
 
     message: Union[None, Unset, str] = UNSET
     contexts: Union[List[str], None, Unset] = UNSET
-    document: Union["APISchemaConversationTurnCreateRequestDocumentType0", None, Unset] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
-        from ..models.api_schema_conversation_turn_create_request_document_type_0 import (
-            APISchemaConversationTurnCreateRequestDocumentType0,
-        )
-
         message: Union[None, Unset, str]
         if isinstance(self.message, Unset):
             message = UNSET
@@ -48,14 +36,6 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             contexts = self.contexts
 
-        document: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.document, Unset):
-            document = UNSET
-        elif isinstance(self.document, APISchemaConversationTurnCreateRequestDocumentType0):
-            document = self.document.to_dict()
-        else:
-            document = self.document
-
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
         field_dict.update({})
@@ -63,17 +43,11 @@ def to_dict(self) -> Dict[str, Any]:
             field_dict["message"] = message
         if contexts is not UNSET:
             field_dict["contexts"] = contexts
-        if document is not UNSET:
-            field_dict["document"] = document
 
         return field_dict
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_conversation_turn_create_request_document_type_0 import (
-            APISchemaConversationTurnCreateRequestDocumentType0,
-        )
-
         d = src_dict.copy()
 
         def _parse_message(data: object) -> Union[None, Unset, str]:
@@ -102,31 +76,13 @@ def _parse_contexts(data: object) -> Union[List[str], None, Unset]:
 
         contexts = _parse_contexts(d.pop("contexts", UNSET))
 
-        def _parse_document(data: object) -> Union["APISchemaConversationTurnCreateRequestDocumentType0", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                document_type_0 = APISchemaConversationTurnCreateRequestDocumentType0.from_dict(data)
-
-                return document_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaConversationTurnCreateRequestDocumentType0", None, Unset], data)
-
-        document = _parse_document(d.pop("document", UNSET))
-
-        api_schema_conversation_turn_create_request = cls(
+        conversation_turn_create_request = cls(
             message=message,
             contexts=contexts,
-            document=document,
         )
 
-        api_schema_conversation_turn_create_request.additional_properties = d
-        return api_schema_conversation_turn_create_request
+        conversation_turn_create_request.additional_properties = d
+        return conversation_turn_create_request
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_response.py b/src/maihem/api_client/maihem_client/models/conversation_turn_create_response.py
similarity index 88%
rename from src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_response.py
rename to src/maihem/api_client/maihem_client/models/conversation_turn_create_response.py
index b5f95c7..a30ec0a 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_response.py
+++ b/src/maihem/api_client/maihem_client/models/conversation_turn_create_response.py
@@ -9,11 +9,11 @@
     from ..models.conversation_nested import ConversationNested
 
 
-T = TypeVar("T", bound="APISchemaConversationTurnCreateResponse")
+T = TypeVar("T", bound="ConversationTurnCreateResponse")
 
 
 @_attrs_define
-class APISchemaConversationTurnCreateResponse:
+class ConversationTurnCreateResponse:
     """
     Attributes:
         conversation (ConversationNested):
@@ -61,13 +61,13 @@ def _parse_turn_id(data: object) -> Union[None, Unset, str]:
 
         turn_id = _parse_turn_id(d.pop("turn_id", UNSET))
 
-        api_schema_conversation_turn_create_response = cls(
+        conversation_turn_create_response = cls(
             conversation=conversation,
             turn_id=turn_id,
         )
 
-        api_schema_conversation_turn_create_response.additional_properties = d
-        return api_schema_conversation_turn_create_response
+        conversation_turn_create_response.additional_properties = d
+        return conversation_turn_create_response
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/criteria.py b/src/maihem/api_client/maihem_client/models/criteria.py
new file mode 100644
index 0000000..dfa356a
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/criteria.py
@@ -0,0 +1,112 @@
+from typing import Any, Dict, List, Type, TypeVar, Union, cast
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+from ..types import UNSET, Unset
+
+T = TypeVar("T", bound="Criteria")
+
+
+@_attrs_define
+class Criteria:
+    """
+    Attributes:
+        id (str):
+        scope_type (str):
+        scope_id (str):
+        criteria (str):
+        criteria_label (str):
+        criteria_description (Union[None, Unset, str]):
+    """
+
+    id: str
+    scope_type: str
+    scope_id: str
+    criteria: str
+    criteria_label: str
+    criteria_description: Union[None, Unset, str] = UNSET
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        id = self.id
+
+        scope_type = self.scope_type
+
+        scope_id = self.scope_id
+
+        criteria = self.criteria
+
+        criteria_label = self.criteria_label
+
+        criteria_description: Union[None, Unset, str]
+        if isinstance(self.criteria_description, Unset):
+            criteria_description = UNSET
+        else:
+            criteria_description = self.criteria_description
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "id": id,
+                "scope_type": scope_type,
+                "scope_id": scope_id,
+                "criteria": criteria,
+                "criteria_label": criteria_label,
+            }
+        )
+        if criteria_description is not UNSET:
+            field_dict["criteria_description"] = criteria_description
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        d = src_dict.copy()
+        id = d.pop("id")
+
+        scope_type = d.pop("scope_type")
+
+        scope_id = d.pop("scope_id")
+
+        criteria = d.pop("criteria")
+
+        criteria_label = d.pop("criteria_label")
+
+        def _parse_criteria_description(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        criteria_description = _parse_criteria_description(d.pop("criteria_description", UNSET))
+
+        criteria = cls(
+            id=id,
+            scope_type=scope_type,
+            scope_id=scope_id,
+            criteria=criteria,
+            criteria_label=criteria_label,
+            criteria_description=criteria_description,
+        )
+
+        criteria.additional_properties = d
+        return criteria
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/criteria_instance_base.py b/src/maihem/api_client/maihem_client/models/criteria_instance_base.py
new file mode 100644
index 0000000..99e1a3c
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/criteria_instance_base.py
@@ -0,0 +1,66 @@
+from typing import Any, Dict, List, Type, TypeVar
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+T = TypeVar("T", bound="CriteriaInstanceBase")
+
+
+@_attrs_define
+class CriteriaInstanceBase:
+    """
+    Attributes:
+        instances (int):
+        conversations (int):
+    """
+
+    instances: int
+    conversations: int
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        instances = self.instances
+
+        conversations = self.conversations
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "instances": instances,
+                "conversations": conversations,
+            }
+        )
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        d = src_dict.copy()
+        instances = d.pop("instances")
+
+        conversations = d.pop("conversations")
+
+        criteria_instance_base = cls(
+            instances=instances,
+            conversations=conversations,
+        )
+
+        criteria_instance_base.additional_properties = d
+        return criteria_instance_base
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_links.py b/src/maihem/api_client/maihem_client/models/links.py
similarity index 95%
rename from src/maihem/api_client/maihem_client/models/api_schema_links.py
rename to src/maihem/api_client/maihem_client/models/links.py
index 9af2021..f0ae3df 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_links.py
+++ b/src/maihem/api_client/maihem_client/models/links.py
@@ -5,11 +5,11 @@
 
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="APISchemaLinks")
+T = TypeVar("T", bound="Links")
 
 
 @_attrs_define
-class APISchemaLinks:
+class Links:
     """
     Attributes:
         test_conversations (Union[None, Unset, str]):
@@ -84,14 +84,14 @@ def _parse_test_result_conversations(data: object) -> Union[None, Unset, str]:
 
         test_result_conversations = _parse_test_result_conversations(d.pop("test_result_conversations", UNSET))
 
-        api_schema_links = cls(
+        links = cls(
             test_conversations=test_conversations,
             test_result=test_result,
             test_result_conversations=test_result_conversations,
         )
 
-        api_schema_links.additional_properties = d
-        return api_schema_links
+        links.additional_properties = d
+        return links
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_metric.py b/src/maihem/api_client/maihem_client/models/metric.py
similarity index 76%
rename from src/maihem/api_client/maihem_client/models/api_schema_metric.py
rename to src/maihem/api_client/maihem_client/models/metric.py
index 297932f..e583c46 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_metric.py
+++ b/src/maihem/api_client/maihem_client/models/metric.py
@@ -1,15 +1,19 @@
-from typing import Any, Dict, List, Type, TypeVar, Union, cast
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar, Union, cast
 
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="APISchemaMetric")
+if TYPE_CHECKING:
+    from ..models.criteria import Criteria
+
+
+T = TypeVar("T", bound="Metric")
 
 
 @_attrs_define
-class APISchemaMetric:
+class Metric:
     """
     Attributes:
         id (str):
@@ -20,6 +24,7 @@ class APISchemaMetric:
         metric (str):
         metric_label (str):
         metric_description (Union[None, Unset, str]):
+        criteria (Union[Unset, List['Criteria']]):
     """
 
     id: str
@@ -30,6 +35,7 @@ class APISchemaMetric:
     metric: str
     metric_label: str
     metric_description: Union[None, Unset, str] = UNSET
+    criteria: Union[Unset, List["Criteria"]] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
@@ -53,6 +59,13 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             metric_description = self.metric_description
 
+        criteria: Union[Unset, List[Dict[str, Any]]] = UNSET
+        if not isinstance(self.criteria, Unset):
+            criteria = []
+            for criteria_item_data in self.criteria:
+                criteria_item = criteria_item_data.to_dict()
+                criteria.append(criteria_item)
+
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
         field_dict.update(
@@ -68,11 +81,15 @@ def to_dict(self) -> Dict[str, Any]:
         )
         if metric_description is not UNSET:
             field_dict["metric_description"] = metric_description
+        if criteria is not UNSET:
+            field_dict["criteria"] = criteria
 
         return field_dict
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.criteria import Criteria
+
         d = src_dict.copy()
         id = d.pop("id")
 
@@ -97,7 +114,14 @@ def _parse_metric_description(data: object) -> Union[None, Unset, str]:
 
         metric_description = _parse_metric_description(d.pop("metric_description", UNSET))
 
-        api_schema_metric = cls(
+        criteria = []
+        _criteria = d.pop("criteria", UNSET)
+        for criteria_item_data in _criteria or []:
+            criteria_item = Criteria.from_dict(criteria_item_data)
+
+            criteria.append(criteria_item)
+
+        metric = cls(
             id=id,
             metric_group=metric_group,
             metric_group_label=metric_group_label,
@@ -106,10 +130,11 @@ def _parse_metric_description(data: object) -> Union[None, Unset, str]:
             metric=metric,
             metric_label=metric_label,
             metric_description=metric_description,
+            criteria=criteria,
         )
 
-        api_schema_metric.additional_properties = d
-        return api_schema_metric
+        metric.additional_properties = d
+        return metric
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_module.py b/src/maihem/api_client/maihem_client/models/module.py
similarity index 94%
rename from src/maihem/api_client/maihem_client/models/api_schema_module.py
rename to src/maihem/api_client/maihem_client/models/module.py
index c191f6e..05dbb2e 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_module.py
+++ b/src/maihem/api_client/maihem_client/models/module.py
@@ -7,11 +7,11 @@
 
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="APISchemaModule")
+T = TypeVar("T", bound="Module")
 
 
 @_attrs_define
-class APISchemaModule:
+class Module:
     """
     Attributes:
         id (str):
@@ -99,7 +99,7 @@ def _parse_description(data: object) -> Union[None, Unset, str]:
 
         description = _parse_description(d.pop("description", UNSET))
 
-        api_schema_module = cls(
+        module = cls(
             id=id,
             created_at=created_at,
             updated_at=updated_at,
@@ -110,8 +110,8 @@ def _parse_description(data: object) -> Union[None, Unset, str]:
             description=description,
         )
 
-        api_schema_module.additional_properties = d
-        return api_schema_module
+        module.additional_properties = d
+        return module
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_module_metrics.py b/src/maihem/api_client/maihem_client/models/module_metrics.py
similarity index 87%
rename from src/maihem/api_client/maihem_client/models/api_schema_module_metrics.py
rename to src/maihem/api_client/maihem_client/models/module_metrics.py
index a5c00fd..092a958 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_module_metrics.py
+++ b/src/maihem/api_client/maihem_client/models/module_metrics.py
@@ -8,14 +8,14 @@
 from ..types import UNSET, Unset
 
 if TYPE_CHECKING:
-    from ..models.api_schema_metric import APISchemaMetric
+    from ..models.metric import Metric
 
 
-T = TypeVar("T", bound="APISchemaModuleMetrics")
+T = TypeVar("T", bound="ModuleMetrics")
 
 
 @_attrs_define
-class APISchemaModuleMetrics:
+class ModuleMetrics:
     """
     Attributes:
         id (str):
@@ -26,7 +26,7 @@ class APISchemaModuleMetrics:
         group_name (str):
         group_label (str):
         description (Union[None, Unset, str]):
-        metrics (Union[Unset, List['APISchemaMetric']]):
+        metrics (Union[Unset, List['Metric']]):
     """
 
     id: str
@@ -37,7 +37,7 @@ class APISchemaModuleMetrics:
     group_name: str
     group_label: str
     description: Union[None, Unset, str] = UNSET
-    metrics: Union[Unset, List["APISchemaMetric"]] = UNSET
+    metrics: Union[Unset, List["Metric"]] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
@@ -90,7 +90,7 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_metric import APISchemaMetric
+        from ..models.metric import Metric
 
         d = src_dict.copy()
         id = d.pop("id")
@@ -119,11 +119,11 @@ def _parse_description(data: object) -> Union[None, Unset, str]:
         metrics = []
         _metrics = d.pop("metrics", UNSET)
         for metrics_item_data in _metrics or []:
-            metrics_item = APISchemaMetric.from_dict(metrics_item_data)
+            metrics_item = Metric.from_dict(metrics_item_data)
 
             metrics.append(metrics_item)
 
-        api_schema_module_metrics = cls(
+        module_metrics = cls(
             id=id,
             created_at=created_at,
             updated_at=updated_at,
@@ -135,8 +135,8 @@ def _parse_description(data: object) -> Union[None, Unset, str]:
             metrics=metrics,
         )
 
-        api_schema_module_metrics.additional_properties = d
-        return api_schema_module_metrics
+        module_metrics.additional_properties = d
+        return module_metrics
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/org.py b/src/maihem/api_client/maihem_client/models/org.py
index 833094a..304fe87 100644
--- a/src/maihem/api_client/maihem_client/models/org.py
+++ b/src/maihem/api_client/maihem_client/models/org.py
@@ -1,12 +1,10 @@
 import datetime
-from typing import Any, Dict, List, Type, TypeVar, Union, cast
+from typing import Any, Dict, List, Type, TypeVar
 
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 from dateutil.parser import isoparse
 
-from ..types import UNSET, Unset
-
 T = TypeVar("T", bound="Org")
 
 
@@ -18,14 +16,14 @@ class Org:
         created_at (datetime.datetime):
         updated_at (datetime.datetime):
         name (str):
-        idp_org_id (Union[None, Unset, str]):
+        idp_org_id (str):
     """
 
     id: str
     created_at: datetime.datetime
     updated_at: datetime.datetime
     name: str
-    idp_org_id: Union[None, Unset, str] = UNSET
+    idp_org_id: str
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
@@ -37,11 +35,7 @@ def to_dict(self) -> Dict[str, Any]:
 
         name = self.name
 
-        idp_org_id: Union[None, Unset, str]
-        if isinstance(self.idp_org_id, Unset):
-            idp_org_id = UNSET
-        else:
-            idp_org_id = self.idp_org_id
+        idp_org_id = self.idp_org_id
 
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
@@ -51,10 +45,9 @@ def to_dict(self) -> Dict[str, Any]:
                 "created_at": created_at,
                 "updated_at": updated_at,
                 "name": name,
+                "idp_org_id": idp_org_id,
             }
         )
-        if idp_org_id is not UNSET:
-            field_dict["idp_org_id"] = idp_org_id
 
         return field_dict
 
@@ -69,14 +62,7 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         name = d.pop("name")
 
-        def _parse_idp_org_id(data: object) -> Union[None, Unset, str]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            return cast(Union[None, Unset, str], data)
-
-        idp_org_id = _parse_idp_org_id(d.pop("idp_org_id", UNSET))
+        idp_org_id = d.pop("idp_org_id")
 
         org = cls(
             id=id,
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations_metric_summaries_type_0.py b/src/maihem/api_client/maihem_client/models/org_create_request.py
similarity index 58%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations_metric_summaries_type_0.py
rename to src/maihem/api_client/maihem_client/models/org_create_request.py
index db9a2ab..60dce58 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations_metric_summaries_type_0.py
+++ b/src/maihem/api_client/maihem_client/models/org_create_request.py
@@ -3,37 +3,52 @@
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
-T = TypeVar("T", bound="APISchemaTestRunResultConversationsMetricSummariesType0")
+T = TypeVar("T", bound="OrgCreateRequest")
 
 
 @_attrs_define
-class APISchemaTestRunResultConversationsMetricSummariesType0:
-    """ """
+class OrgCreateRequest:
+    """
+    Attributes:
+        name (str):
+    """
 
-    additional_properties: Dict[str, str] = _attrs_field(init=False, factory=dict)
+    name: str
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
+        name = self.name
+
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "name": name,
+            }
+        )
 
         return field_dict
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
-        api_schema_test_run_result_conversations_metric_summaries_type_0 = cls()
+        name = d.pop("name")
+
+        org_create_request = cls(
+            name=name,
+        )
 
-        api_schema_test_run_result_conversations_metric_summaries_type_0.additional_properties = d
-        return api_schema_test_run_result_conversations_metric_summaries_type_0
+        org_create_request.additional_properties = d
+        return org_create_request
 
     @property
     def additional_keys(self) -> List[str]:
         return list(self.additional_properties.keys())
 
-    def __getitem__(self, key: str) -> str:
+    def __getitem__(self, key: str) -> Any:
         return self.additional_properties[key]
 
-    def __setitem__(self, key: str, value: str) -> None:
+    def __setitem__(self, key: str, value: Any) -> None:
         self.additional_properties[key] = value
 
     def __delitem__(self, key: str) -> None:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_user.py b/src/maihem/api_client/maihem_client/models/user.py
similarity index 95%
rename from src/maihem/api_client/maihem_client/models/api_schema_user.py
rename to src/maihem/api_client/maihem_client/models/user.py
index fe6bf11..5413829 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_user.py
+++ b/src/maihem/api_client/maihem_client/models/user.py
@@ -7,11 +7,11 @@
 
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="APISchemaUser")
+T = TypeVar("T", bound="User")
 
 
 @_attrs_define
-class APISchemaUser:
+class User:
     """
     Attributes:
         id (str):
@@ -99,7 +99,7 @@ def _parse_image_url(data: object) -> Union[None, Unset, str]:
 
         image_url = _parse_image_url(d.pop("image_url", UNSET))
 
-        api_schema_user = cls(
+        user = cls(
             id=id,
             created_at=created_at,
             updated_at=updated_at,
@@ -110,8 +110,8 @@ def _parse_image_url(data: object) -> Union[None, Unset, str]:
             image_url=image_url,
         )
 
-        api_schema_user.additional_properties = d
-        return api_schema_user
+        user.additional_properties = d
+        return user
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_user_profile.py b/src/maihem/api_client/maihem_client/models/user_profile.py
similarity index 54%
rename from src/maihem/api_client/maihem_client/models/api_schema_user_profile.py
rename to src/maihem/api_client/maihem_client/models/user_profile.py
index 1591182..4025461 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_user_profile.py
+++ b/src/maihem/api_client/maihem_client/models/user_profile.py
@@ -4,36 +4,44 @@
 from attrs import field as _attrs_field
 
 if TYPE_CHECKING:
-    from ..models.api_schema_org import APISchemaOrg
-    from ..models.api_schema_user import APISchemaUser
+    from ..models.org import Org
+    from ..models.user import User
 
 
-T = TypeVar("T", bound="APISchemaUserProfile")
+T = TypeVar("T", bound="UserProfile")
 
 
 @_attrs_define
-class APISchemaUserProfile:
+class UserProfile:
     """
     Attributes:
-        user (APISchemaUser):
-        org (APISchemaOrg):
+        user (User):
+        active_org_id (str):
+        orgs (List['Org']):
     """
 
-    user: "APISchemaUser"
-    org: "APISchemaOrg"
+    user: "User"
+    active_org_id: str
+    orgs: List["Org"]
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
         user = self.user.to_dict()
 
-        org = self.org.to_dict()
+        active_org_id = self.active_org_id
+
+        orgs = []
+        for orgs_item_data in self.orgs:
+            orgs_item = orgs_item_data.to_dict()
+            orgs.append(orgs_item)
 
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
         field_dict.update(
             {
                 "user": user,
-                "org": org,
+                "active_org_id": active_org_id,
+                "orgs": orgs,
             }
         )
 
@@ -41,21 +49,29 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_org import APISchemaOrg
-        from ..models.api_schema_user import APISchemaUser
+        from ..models.org import Org
+        from ..models.user import User
 
         d = src_dict.copy()
-        user = APISchemaUser.from_dict(d.pop("user"))
+        user = User.from_dict(d.pop("user"))
+
+        active_org_id = d.pop("active_org_id")
+
+        orgs = []
+        _orgs = d.pop("orgs")
+        for orgs_item_data in _orgs:
+            orgs_item = Org.from_dict(orgs_item_data)
 
-        org = APISchemaOrg.from_dict(d.pop("org"))
+            orgs.append(orgs_item)
 
-        api_schema_user_profile = cls(
+        user_profile = cls(
             user=user,
-            org=org,
+            active_org_id=active_org_id,
+            orgs=orgs,
         )
 
-        api_schema_user_profile.additional_properties = d
-        return api_schema_user_profile
+        user_profile.additional_properties = d
+        return user_profile
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/cli.py b/src/maihem/cli.py
new file mode 100644
index 0000000..5a0b97f
--- /dev/null
+++ b/src/maihem/cli.py
@@ -0,0 +1,176 @@
+import click
+from maihem.clients import Maihem
+from maihem.utils.utils import import_wrapper_function, create_project_folder
+from maihem.errors import RequestValidationError
+
+
+# Create the main CLI group
+@click.group()
+@click.option(
+    "--env",
+    type=click.Choice(["local", "staging", "production"]),
+    default="production",
+    help="Environment to use (default: production)",
+)
+@click.pass_context
+def cli(ctx, env):
+    """Maihem CLI"""
+    try:
+        ctx.obj = Maihem(env=env)
+    except RequestValidationError as e:
+        click.echo(e)
+        ctx.exit(1)
+
+
+# Target agent commands
+@cli.group()
+def target_agent():
+    """Manage target agents"""
+    pass
+
+
+@target_agent.command()
+@click.option("--name", required=True, help="Unique name of the target agent")
+@click.option("--label", help="Label for the target agent (optional)")
+@click.option("--role", required=True, help="Role of the target agent")
+@click.option("--description", required=True, help="Description of the target agent")
+@click.option("--language", default="en", help="Language (default: en). Follow ISO 639")
+@click.pass_obj
+def create(maihem_client, name, label, role, description, language):
+    """Create a target agent"""
+    maihem_client.create_target_agent(
+        name=name, label=label, role=role, description=description, language=language
+    )
+    create_project_folder(name)
+
+
+# Test commands
+@cli.group()
+def test():
+    """Manage tests"""
+    pass
+
+
+@test.command()
+@click.option("--name", required=True, help="Name of the test")
+@click.option("--label", help="Label for the test (optional)")
+@click.option("--target-agent-name", required=True, help="Name of the target agent")
+@click.option(
+    "--initiating-agent",
+    type=click.Choice(["maihem", "target"]),
+    default="maihem",
+    help="Initiating agent (maihem or target)",
+)
+@click.option("--modules", required=True, help="Modules to use")
+@click.option(
+    "--documents-path", required=False, help="Path to the folder with documents"
+)
+@click.option(
+    "--number-conversations", type=int, required=True, help="Number of conversations"
+)
+@click.option(
+    "--conversation-turns-max",
+    type=int,
+    default=10,
+    help="Max turns per conversation (default: 10)",
+)
+@click.option(
+    "--maihem-behavior-prompt",
+    help="Prompt for the maihem agent behavior",
+)
+@click.option(
+    "--maihem-goal-prompt",
+    help="Describes the goal of the simulated personas",
+)
+@click.option(
+    "--maihem-population-prompt",
+    help="Describes the desired population of simulated personas",
+)
+@click.pass_obj
+def create(
+    maihem_client,
+    name,
+    label,
+    target_agent_name,
+    initiating_agent,
+    modules,
+    documents_path,
+    number_conversations,
+    conversation_turns_max,
+    maihem_behavior_prompt,
+    maihem_goal_prompt,
+    maihem_population_prompt,
+):
+    """Create a test"""
+    module_list = [m.strip() for m in modules.split(",")]
+    maihem_client.create_test(
+        name=name,
+        label=label,
+        modules=module_list,
+        target_agent_name=target_agent_name,
+        initiating_agent=initiating_agent,
+        documents_path=documents_path,
+        conversation_turns_max=conversation_turns_max,
+        number_conversations=number_conversations,
+        maihem_behavior_prompt=maihem_behavior_prompt,
+        maihem_goal_prompt=maihem_goal_prompt,
+        maihem_population_prompt=maihem_population_prompt,
+    )
+
+
+@test.command()
+@click.option("--name", required=True, help="Name of the test run")
+@click.option("--label", help="Label for the test run (optional)")
+@click.option("--test-name", required=True, help="Name of the test")
+@click.option(
+    "--wrapper-function-path",
+    default="wrapper_function.py",
+    help="Path to the wrapper function",
+)
+@click.option(
+    "--concurrent-conversations",
+    type=int,
+    default=10,
+    help="Number of concurrent conversations",
+)
+@click.pass_obj
+def run(
+    maihem_client,
+    name,
+    label,
+    test_name,
+    wrapper_function_path,
+    concurrent_conversations,
+):
+    """Run a test"""
+    wrapper_function = import_wrapper_function(wrapper_function_path)
+    maihem_client.run_test(
+        name=name,
+        label=label,
+        test_name=test_name,
+        wrapper_function=wrapper_function,
+        concurrent_conversations=concurrent_conversations,
+    )
+
+
+# Test run commands
+@cli.group()
+def test_run():
+    """Manage test runs"""
+    pass
+
+
+@test_run.command()
+@click.option("--test-name", required=True, help="Name of the test")
+@click.option("--test-run-name", required=True, help="Name of the test run")
+@click.pass_obj
+def get(maihem_client, test_name, test_run_name):
+    """Get test run results"""
+    test_run_results = maihem_client.get_test_run_result(
+        test_name=test_name, test_run_name=test_run_name
+    )
+    click.echo(test_run_results)
+
+
+if __name__ == "__main__":
+    cli()
diff --git a/src/maihem/clients.py b/src/maihem/clients.py
index a82f15f..244f5ef 100644
--- a/src/maihem/clients.py
+++ b/src/maihem/clients.py
@@ -1,29 +1,32 @@
 from concurrent.futures import ThreadPoolExecutor, as_completed
 import os
-from typing import Dict, Literal, Optional, List, Tuple
+from typing import Dict, Literal, Optional, List, Callable
 from pydantic import ValidationError
 import random
 from tqdm import tqdm
 from yaspin import yaspin
 from yaspin.spinners import Spinners
 
+from maihem.modules_map import map_module_list_to_metrics
 from maihem.schemas.agents import TargetAgent, AgentType
 from maihem.schemas.tests import (
     Test,
     TestRun,
-    TestRunResultConversations,
-    TestRunResultMetrics,
     TestRunConversations,
+    ResultTestRun,
 )
 from maihem.schemas.conversations import ConversationTurnCreateResponse
-from maihem.api_client.maihem_client.models.api_schema_agent_target_create_request import (
-    APISchemaAgentTargetCreateRequest,
+from maihem.api_client.maihem_client.models.agent_target_create_request import (
+    AgentTargetCreateRequest,
 )
-from maihem.api_client.maihem_client.models.api_schema_test_create_request import (
-    APISchemaTestCreateRequest,
+from maihem.api_client.maihem_client.models.test_create_request import (
+    TestCreateRequest,
 )
-from maihem.api_client.maihem_client.models.api_schema_test_create_request_metrics_config import (
-    APISchemaTestCreateRequestMetricsConfig,
+from maihem.api_client.maihem_client.models.test_create_request_metrics_config import (
+    TestCreateRequestMetricsConfig,
+)
+from maihem.api_client.maihem_client.models.create_test_run_request import (
+    CreateTestRunRequest,
 )
 from maihem.api_client.maihem_client.models.conversation_nested import (
     ConversationNested,
@@ -35,7 +38,7 @@
 from maihem.api import MaihemHTTPClientSync
 from maihem.schemas.tests import TestStatusEnum
 from maihem.logger import get_logger
-from maihem.utils import TextSplitter, extract_text
+from maihem.utils.documents import TextSplitter, extract_text, parse_documents
 
 
 class Client:
@@ -43,54 +46,85 @@ class Client:
     _base_url_ui: str = "https://cause.maihem.ai"
     _api_key: str = None
 
+    _staging_url: str = "https://api.staging.maihem.ai"
+    _staging_url_ui: str = "https://cause.staging.maihem.ai"
+
+    _local_url: str = "http://localhost:8000"
+    _local_url_ui: str = "http://localhost:3000"
+
     def create_target_agent(
         self,
-        identifier: str,
+        name: str,
         role: str,
-        industry: str,
         description: str,
+        label: str,
+        language: str,
     ) -> TargetAgent:
         pass
 
-    def get_target_agent(self, identifier: str) -> TargetAgent:
+    def get_target_agent(self, name: str) -> TargetAgent:
         # Add implementation here
         raise NotImplementedError("Method not implemented")
 
     def create_test(
         self,
-        test_identifier: str,
+        name: str,
+        target_agent_name: str,
         initiating_agent: Literal["maihem", "target"],
-        agent_maihem_behavior_prompt: str = None,
-        conversation_turns_max: int = 10,
+        label: Optional[str] = None,
+        modules: str = None,
         metrics_config: Dict = None,
+        maihem_agent_behavior_prompt: str = None,
+        maihem_agent_goal_prompt: str = None,
+        maihem_agent_population_prompt: str = None,
+        conversation_turns_max: int = 10,
+        number_conversations: int = 12,
     ) -> Test:
         raise NotImplementedError("Method not implemented")
 
-    def create_test_run(
+    def run_test(
         self,
-        test_identifier: str,
-        agent_target: TargetAgent,
-        concurrent_conversations: int,
+        name: str,
+        test_name: str,
+        wrapper_function: Callable,
+        label: Optional[str] = None,
+        concurrent_conversations: int = 10,
     ) -> TestRun:
         raise NotImplementedError("Method not implemented")
 
-    def get_test_run_result(self, test_run_id: str) -> TestRun:
+    def get_test_run_result(self, test_name: str, test_run_name: str) -> TestRun:
         raise NotImplementedError("Method not implemented")
 
 
 class Maihem(Client):
     _maihem_api_client = MaihemHTTPClientSync
 
-    def __init__(self, api_key: Optional[str] = None) -> None:
-        self._api_key = api_key or os.getenv("MAIHEM_API_KEY")
+    def __init__(
+        self,
+        env: Optional[Literal["production", "staging", "local"]] = "production",
+        api_key: Optional[str] = None,
+    ) -> None:
+        self._logger = get_logger()
 
-        if not self._api_key:
-            raise errors.raise_request_validation_error(
-                "API key is required to initialize Maihem client"
+        if env == "production":
+            self._api_key = api_key or os.getenv("MAIHEM_API_KEY")
+            if not self._api_key:
+                raise errors.raise_request_validation_error("API key is missing")
+            self._maihem_api_client = MaihemHTTPClientSync(
+                self._base_url, self._api_key
             )
-
-        self._maihem_api_client = MaihemHTTPClientSync(self._base_url, self._api_key)
-        self._logger = get_logger()
+        elif env == "staging":
+            self._api_key = api_key or os.getenv("MAIHEM_API_KEY_STAGING")
+            if not self._api_key:
+                raise errors.raise_request_validation_error("Staging API key missing")
+            self._override_base_url(self._staging_url)
+            self._override_base_url_ui(self._staging_url_ui)
+        elif env == "local":
+            self._api_key = api_key or os.getenv("MAIHEM_API_KEY_LOCAL")
+            if not self._api_key:
+                raise errors.raise_request_validation_error("Local API key missing")
+            self._override_base_url(self._local_url)
+            self._override_base_url_ui(self._local_url_ui)
 
     def _override_base_url(self, base_url: str) -> None:
         self._base_url = base_url
@@ -101,23 +135,21 @@ def _override_base_url_ui(self, base_url_ui: str) -> None:
 
     def create_target_agent(
         self,
-        identifier: str,
+        name: str,
         role: str,
-        industry: str,
         description: str,
-        name: Optional[str] = None,
+        label: Optional[str] = None,
         language: Optional[str] = "en",
     ) -> TargetAgent:
         logger = get_logger()
-        logger.info(f"Creating target agent {identifier}...")
+        logger.info(f"Creating target agent '{name}'...")
         resp = None
         try:
             resp = self._maihem_api_client.create_agent_target(
-                req=APISchemaAgentTargetCreateRequest(
-                    identifier=identifier,
+                req=AgentTargetCreateRequest(
                     name=name,
                     role=role,
-                    industry=industry,
+                    label=label,
                     description=description,
                     language=language,
                 )
@@ -132,51 +164,13 @@ def create_target_agent(
         except ValidationError as e:
             errors.handle_schema_validation_error(e)
 
-        logger.info(f"Successfully created target agent {identifier}!")
+        logger.info(f"Successfully created target agent '{name}'")
         return agent_target
 
-    def upsert_target_agent(
-        self,
-        identifier: str,
-        role: str,
-        industry: str,
-        description: str,
-        name: Optional[str] = None,
-        language: Optional[str] = "en",
-    ) -> TargetAgent:
-        logger = get_logger()
-        logger.info(f"Creating target agent {identifier}...")
+    def get_target_agent(self, name: str) -> TargetAgent:
         resp = None
         try:
-            resp = self._maihem_api_client.upsert_agent_target(
-                req=APISchemaAgentTargetCreateRequest(
-                    identifier=identifier,
-                    name=name,
-                    role=role,
-                    industry=industry,
-                    description=description,
-                    language=language,
-                )
-            )
-        except errors.ErrorBase as e:
-            errors.handle_base_error(e)
-
-        agent_target = None
-
-        try:
-            agent_target = TargetAgent.model_validate(resp.to_dict())
-        except ValidationError as e:
-            errors.handle_schema_validation_error(e)
-
-        logger.info(f"Successfully created target agent {identifier}!")
-        return agent_target
-
-    def get_target_agent(self, identifier: str) -> TargetAgent:
-        resp = None
-        try:
-            resp = self._maihem_api_client.get_agent_target_by_identifier(
-                identifier=identifier
-            )
+            resp = self._maihem_api_client.get_agent_target_by_name(name=name)
         except errors.ErrorBase as e:
             errors.handle_base_error(e)
 
@@ -191,104 +185,89 @@ def get_target_agent(self, identifier: str) -> TargetAgent:
 
     def create_test(
         self,
-        identifier: str,
-        target_agent_identifier: str,
-        initiating_agent: AgentType = AgentType.MAIHEM,
-        name: Optional[str] = None,
-        maihem_agent_behavior_prompt: Optional[str] = None,
-        conversation_turns_max: Optional[int] = 10,
+        name: str,
+        target_agent_name: str,
+        initiating_agent: Optional[AgentType] = AgentType.MAIHEM,
+        label: Optional[str] = None,
+        modules: Optional[List[str]] = None,
         metrics_config: Optional[Dict] = None,
+        maihem_behavior_prompt: Optional[str] = None,
+        maihem_goal_prompt: Optional[str] = None,
+        maihem_population_prompt: Optional[str] = None,
+        conversation_turns_max: Optional[int] = 4,
+        number_conversations: Optional[int] = 10,
+        documents_path: Optional[str] = None,
     ) -> Test:
-        resp = None
         logger = get_logger()
-        logger.info(f"Creating test {identifier}...")
-
+        logger.info(f"Creating test '{name}'...")
+
+        # Input validation using pattern matching
+        match (modules, metrics_config):
+            case (None, None):
+                raise ValueError("Either modules or metrics_config must be provided")
+            case (list(), dict()):
+                raise ValueError("Cannot provide both modules and metrics_config")
+            case (list(), None):
+                if not modules:
+                    raise ValueError("Modules list must not be empty")
+                metrics_config = map_module_list_to_metrics(
+                    modules, number_conversations
+                )
+            case (None, dict()):
+                if not metrics_config:
+                    raise ValueError("Metrics config must not be empty")
+                if not all(
+                    isinstance(v, int) and v > 0 for v in metrics_config.values()
+                ):
+                    raise ValueError("Metrics config values must be positive integers")
+            case _:
+                raise ValueError("Invalid configuration for modules or metrics_config")
+
+        # Convert string initiating_agent to enum if needed
         if isinstance(initiating_agent, str):
             try:
                 initiating_agent = AgentType[initiating_agent.upper()]
-            except KeyError as e:
+            except KeyError:
                 raise errors.raise_request_validation_error(
                     f"Invalid agent type: {initiating_agent}"
-                ) from e
+                )
 
         try:
-            target_agent = self._maihem_api_client.get_agent_target_by_identifier(
-                identifier=target_agent_identifier
+            target_agent = self._maihem_api_client.get_agent_target_by_name(
+                name=target_agent_name
             )
 
             if not target_agent:
                 raise errors.raise_not_found_error(
-                    f"Target agent {target_agent_identifier} not found"
+                    f"Target agent '{target_agent_name}' not found"
                 )
 
-            metrics_config = APISchemaTestCreateRequestMetricsConfig.from_dict(
-                metrics_config
-            )
-            resp = self._maihem_api_client.create_test(
-                req=APISchemaTestCreateRequest(
-                    identifier=identifier,
-                    name=name,
-                    initiating_agent=initiating_agent,
-                    conversation_turns_max=conversation_turns_max,
-                    agent_target_id=target_agent.id,
-                    agent_maihem_behavior_prompt=maihem_agent_behavior_prompt,
-                    metrics_config=metrics_config,
+            if documents_path:
+                documents = parse_documents(documents_path)
+            else:
+                documents = None
+
+            with yaspin(
+                Spinners.arc,
+                text="Creating Test, this might take a minute...",
+            ) as _:
+                metrics_config_req = TestCreateRequestMetricsConfig.from_dict(
+                    metrics_config
                 )
-            )
-        except errors.ErrorBase as e:
-            errors.handle_base_error(e)
-
-        test = None
-
-        try:
-            test = Test.model_validate(resp.to_dict())
-        except ValidationError as e:
-            errors.handle_schema_validation_error(e)
-
-        logger.info(f"Successfull created test {identifier}!")
-        return test
-
-    def upsert_test(
-        self,
-        identifier: str,
-        target_agent_identifier: str,
-        initiating_agent: AgentType = AgentType.MAIHEM,
-        name: Optional[str] = None,
-        maihem_agent_behavior_prompt: Optional[str] = None,
-        conversation_turns_max: Optional[int] = 10,
-        metrics_config: Optional[Dict] = None,
-    ) -> Test:
-        resp = None
-        logger = get_logger()
-        logger.info(f"Creating test {identifier}...")
-
-        if isinstance(initiating_agent, str):
-            try:
-                initiating_agent = AgentType[initiating_agent.upper()]
-            except KeyError as e:
-                raise errors.raise_request_validation_error(
-                    f"Invalid agent type: {initiating_agent}"
-                ) from e
-
-        try:
-            target_agent = self._maihem_api_client.get_agent_target_by_identifier(
-                identifier=target_agent_identifier
-            )
-            metrics_config = APISchemaTestCreateRequestMetricsConfig.from_dict(
-                metrics_config
-            )
-            resp = self._maihem_api_client.upsert_test(
-                req=APISchemaTestCreateRequest(
-                    identifier=identifier,
-                    name=name,
-                    initiating_agent=initiating_agent,
-                    conversation_turns_max=conversation_turns_max,
-                    agent_target_id=target_agent.id,
-                    agent_maihem_behavior_prompt=maihem_agent_behavior_prompt,
-                    metrics_config=metrics_config,
-                    is_dev_mode=True,
+                resp = self._maihem_api_client.create_test(
+                    req=TestCreateRequest(
+                        name=name,
+                        label=label,
+                        initiating_agent=initiating_agent,
+                        conversation_turns_max=conversation_turns_max,
+                        agent_target_id=target_agent.id,
+                        agent_maihem_behavior_prompt=maihem_behavior_prompt,
+                        agent_maihem_goal_prompt=maihem_goal_prompt,
+                        agent_maihem_population_prompt=maihem_population_prompt,
+                        metrics_config=metrics_config_req,
+                        documents=documents if documents else None,
+                    )
                 )
-            )
         except errors.ErrorBase as e:
             errors.handle_base_error(e)
 
@@ -299,12 +278,13 @@ def upsert_test(
         except ValidationError as e:
             errors.handle_schema_validation_error(e)
 
+        logger.info(f"Successfully created test '{name}'")
         return test
 
-    def get_test(self, identifier: str) -> Test:
+    def get_test(self, name: str) -> Test:
         resp = None
         try:
-            resp = self._maihem_api_client.get_test_by_identifier(identifier=identifier)
+            resp = self._maihem_api_client.get_test_by_name(name=name)
         except errors.ErrorBase as e:
             errors.handle_base_error(e)
 
@@ -317,27 +297,35 @@ def get_test(self, identifier: str) -> Test:
 
         return test
 
-    def create_test_run(
+    def run_test(
         self,
-        test_identifier: str,
-        target_agent: TargetAgent,
-        concurrent_conversations: int = 1,
-    ) -> TestRun:
+        name: str,
+        test_name: str,
+        wrapper_function: Callable,
+        label: Optional[str] = None,
+        concurrent_conversations: int = 10,
+    ) -> ResultTestRun:
         logger = get_logger()
         test_run = None
         try:
-            test = self._maihem_api_client.get_test_by_identifier(test_identifier)
-
-            resp = None
-
-            logger.info(f"Spawning test run for test {test.identifier}...")
+            with yaspin(
+                Spinners.arc,
+                text=f"Preparing test run '{test_name}...",
+            ) as _:
+                test = self._maihem_api_client.get_test_by_name(name=test_name)
+                target_agent = self.get_target_agent(name=test.agent_target_name)
+                target_agent.set_wrapper_function(wrapper_function=wrapper_function)
+                resp = None
 
             try:
                 with yaspin(
                     Spinners.arc,
-                    text="Creating Maihem Agents, this might take a minute...",
-                ) as sp:
-                    resp = self._maihem_api_client.create_test_run(test_id=test.id)
+                    text="Creating Test Run, this might take a minute...",
+                ) as _:
+                    resp = self._maihem_api_client.create_test_run(
+                        test_id=test.id,
+                        req=CreateTestRunRequest(name=name, label=label),
+                    )
             except errors.ErrorBase as e:
                 errors.handle_base_error(e)
 
@@ -349,7 +337,7 @@ def create_test_run(
             test_run_conversations = self.get_test_run_conversations(test_run.id)
             conversation_ids = test_run_conversations.conversation_ids
 
-            logger.info(f"Test run spawned for test {test.identifier}!")
+            logger.info(f"Starting test run '{test.name}'")
             print("\n" + "-" * 50 + "\n")
             logger.info(
                 f"Running test run with {len(conversation_ids)} conversations (up to {concurrent_conversations} concurrently)..."
@@ -361,6 +349,8 @@ def create_test_run(
 
             print("\n" + "-" * 50 + "\n")
 
+            conversation_history = {}
+
             with tqdm(
                 len(conversation_ids),
                 total=len(conversation_ids),
@@ -380,6 +370,7 @@ def create_test_run(
                             test,
                             target_agent,
                             progress_bar_position=i + 1,
+                            conversation_history=conversation_history,
                         ): conversation_id
                         for i, conversation_id in enumerate(conversation_ids)
                     }
@@ -397,97 +388,13 @@ def create_test_run(
                             progress.update()
 
             print("\n" + "-" * 50 + "\n")
-            logger.info(f"Test run ({test_run.id}) completed!")
-            return test_run
-        except KeyboardInterrupt:
-            logger.info("Keyboard interrupt detected. Canceling test...")
-            if test_run is not None and test_run.id is not None:
-                self._maihem_api_client.update_test_run_status(
-                    test_run_id=test_run.id, status=TestStatusEnum.CANCELED
-                )
-            logger.info("Test run canceled!")
-        except Exception as e:
-            logger.error(f"Error: {e}. Ending test...")
-            if test_run is not None and test_run.id is not None:
-                self._maihem_api_client.update_test_run_status(
-                    test_run_id=test_run.id, status=TestStatusEnum.ERROR
-                )
-
-    def create_test_run_dev_mode(
-        self,
-        test_identifier: str,
-        target_agent: TargetAgent,
-        concurrent_conversations: int = 1,
-    ) -> TestRun:
-        logger = get_logger()
-        test_run = None
-        try:
-            if not target_agent._chat_function:
-                errors.raise_request_validation_error(
-                    "Chat function the target agent must be passed."
-                )
+            logger.info(f"Test run '{name}' completed")
 
-            test = self._maihem_api_client.get_test_by_identifier(test_identifier)
+            url_results = f"https://cause.maihem.ai/evaluate/test-runs/{test_run.id}"
+            logger.info(f"See test run results: {url_results}")
 
-            resp = None
+            return self.get_test_run_result(test_name=test_name, test_run_name=name)
 
-            try:
-                with yaspin(
-                    Spinners.arc,
-                    text="Creating Maihem Agent, this might take a minute...",
-                ) as sp:
-                    resp = self._maihem_api_client.create_test_run(test_id=test.id)
-            except errors.ErrorBase as e:
-                errors.handle_base_error(e)
-
-            try:
-                test_run = TestRun.model_validate(resp.to_dict())
-            except ValidationError as e:
-                errors.handle_schema_validation_error(e)
-
-            test_run_conversations = self.get_test_run_conversations(test_run.id)
-            conversation_ids = test_run_conversations.conversation_ids
-
-            # logger.info(
-            #     f"Test run results (UI): {self._base_url_ui}/evaluations/{test_run.id}"
-            # )
-
-            # with tqdm(
-            #     len(conversation_ids),
-            #     total=len(conversation_ids),
-            #     unit="conversation",
-            #     colour="green",
-            #     desc=f"Test run ({test_run.id})",
-            #     position=0,
-            # ) as progress:
-            with ThreadPoolExecutor(max_workers=concurrent_conversations) as executor:
-                future_to_conversation_id = {
-                    executor.submit(
-                        self._run_conversation,
-                        test_run.id,
-                        conversation_id,
-                        test,
-                        target_agent,
-                        progress_bar_position=i + 1,
-                    ): conversation_id
-                    for i, conversation_id in enumerate(conversation_ids)
-                }
-
-                for future in as_completed(future_to_conversation_id):
-                    conversation_id = future_to_conversation_id[future]
-                    try:
-                        future.result()
-                    except errors.ErrorBase as e:
-                        logger.error(
-                            f"Error running conversation ({conversation_id}): {e.message}"
-                        )
-                        # progress.colour = "red"
-                    # finally:
-                    # progress.update()
-
-            print("\n" + "-" * 50 + "\n")
-            logger.info(f"Conversation ({test_run.id}) completed!")
-            return test_run
         except KeyboardInterrupt:
             logger.info("Keyboard interrupt detected. Canceling test...")
             if test_run is not None and test_run.id is not None:
@@ -495,6 +402,8 @@ def create_test_run_dev_mode(
                     test_run_id=test_run.id, status=TestStatusEnum.CANCELED
                 )
             logger.info("Test run canceled!")
+        except errors.ErrorBase as e:
+            errors.handle_base_error(e)
         except Exception as e:
             logger.error(f"Error: {e}. Ending test...")
             if test_run is not None and test_run.id is not None:
@@ -519,57 +428,73 @@ def get_test_run_conversations(self, test_run_id: str) -> TestRunConversations:
 
         return test_run
 
-    def get_test_run_result(self, test_run_id: str) -> TestRunResultMetrics:
-        resp = None
-
+    def get_test_run_result(self, test_name: str, test_run_name: str) -> ResultTestRun:
         try:
-            resp = self._maihem_api_client.get_test_run_result(test_run_id)
+            test = self.get_test(test_name)
         except errors.ErrorBase as e:
             errors.handle_base_error(e)
 
-        test_run = None
-
         try:
-            test_run = TestRunResultMetrics.model_validate(resp.to_dict())
-        except ValidationError as e:
-            errors.handle_schema_validation_error(e)
-
-        return test_run
+            test_runs = self._maihem_api_client.get_test_test_runs(
+                test_id=test.id, test_run_name=test_run_name
+            )
+            if test_runs is None or len(test_runs) == 0:
+                errors.raise_not_found_error(
+                    f"Test run '{test_run_name}' not found for test '{test_name}'"
+                )
+        except errors.ErrorBase as e:
+            errors.handle_base_error(e)
 
-    def get_test_run_result_conversations(
-        self, test_run_id: str
-    ) -> TestRunResultConversations:
-        resp = None
         test_run = None
 
         try:
-            resp = self._maihem_api_client.get_test_run_result_conversations(
-                test_run_id
+            test_run_api = self._maihem_api_client.get_test_run_result(
+                test_run_id=test_runs[0].id
             )
         except errors.ErrorBase as e:
             errors.handle_base_error(e)
 
         try:
-            resp_conversations = resp.conversations
-            resp_dict = resp.to_dict()
-            resp_dict["conversations"] = []
-
-            conversation_nesteds: ConversationNested = []
-            for conv in resp_conversations:
-                conv_dict = conv.to_dict()
-                try:
-                    conv = ConversationNested.from_dict(conv_dict)
-                    conversation_nesteds.append(conv)
-                except ValidationError as e:
-                    errors.handle_schema_validation_error(e)
-
-            test_run = TestRunResultConversations.model_validate(resp_dict)
-            test_run.conversations = conversation_nesteds
+            test_run = ResultTestRun(test_run_api=test_run_api)
         except ValidationError as e:
             errors.handle_schema_validation_error(e)
 
         return test_run
 
+    # def get_test_run_result_conversations(
+    #     self, test_run_id: str
+    # ) -> TestRunResultConversations:
+    #     resp = None
+    #     test_run = None
+
+    #     try:
+    #         resp = self._maihem_api_client.get_test_run_result_conversations(
+    #             test_run_id
+    #         )
+    #     except errors.ErrorBase as e:
+    #         errors.handle_base_error(e)
+
+    #     try:
+    #         resp_conversations = resp.conversations
+    #         resp_dict = resp.to_dict()
+    #         resp_dict["conversations"] = []
+
+    #         conversation_nesteds: ConversationNested = []
+    #         for conv in resp_conversations:
+    #             conv_dict = conv.to_dict()
+    #             try:
+    #                 conv = ConversationNested.from_dict(conv_dict)
+    #                 conversation_nesteds.append(conv)
+    #             except ValidationError as e:
+    #                 errors.handle_schema_validation_error(e)
+
+    #         test_run = TestRunResultConversations.model_validate(resp_dict)
+    #         test_run.conversations = conversation_nesteds
+    #     except ValidationError as e:
+    #         errors.handle_schema_validation_error(e)
+
+    #     return test_run
+
     def get_conversation(self, conversation_id: str) -> ConversationNested:
         resp = None
 
@@ -591,6 +516,7 @@ def _run_conversation(
         test: Test,
         target_agent: TargetAgent,
         progress_bar_position: int,
+        conversation_history: Dict,
     ) -> str:
         is_conversation_active = True
         previous_turn_id = None
@@ -612,6 +538,7 @@ def _run_conversation(
                 test=test,
                 target_agent=target_agent,
                 previous_turn_id=previous_turn_id,
+                conversation_history=conversation_history,
             )
 
             if (
@@ -635,6 +562,7 @@ def _run_conversation_turn(
         conversation_id: str,
         test: Test,
         target_agent: TargetAgent,
+        conversation_history: Dict,
         previous_turn_id: Optional[str] = None,
     ) -> ConversationTurnCreateResponse:
         agent_maihem_message = None
@@ -687,7 +615,6 @@ def _run_conversation_turn(
                 conversation_id=conversation_id,
                 target_agent_message=None,
                 contexts=[],
-                document={document_key: text} if document_key else None,
             )
 
             agent_maihem_message = self._get_conversation_message_from_conversation(
@@ -707,15 +634,14 @@ def _run_conversation_turn(
             )
 
         try:
-            target_agent_message, contexts = self._send_target_agent_message(
-                target_agent,
-                conversation_id,
-                agent_maihem_message=(
-                    agent_maihem_message.content if agent_maihem_message else None
-                ),
+            agent_maihem_message = (
+                agent_maihem_message.content if agent_maihem_message else None
+            )
+            target_agent_message, contexts = target_agent._send_message(
+                conversation_id, agent_maihem_message, conversation_history
             )
         except Exception as e:
-            errors.raise_chat_function_error(
+            errors.raise_wrapper_function_error(
                 f"Error sending message to target agent: {e}"
             )
 
@@ -731,7 +657,6 @@ def _run_conversation_turn(
             conversation_id=conversation_id,
             target_agent_message=target_agent_message,
             contexts=contexts,
-            document={document_key: text} if document_key else None,
         )
 
         return turn_resp
@@ -742,7 +667,6 @@ def _generate_conversation_turn(
         conversation_id: str,
         target_agent_message: Optional[str] = None,
         contexts: Optional[List[str]] = None,
-        document: Optional[Dict] = None,
     ) -> ConversationTurnCreateResponse:
         try:
             resp = self._maihem_api_client.create_conversation_turn(
@@ -750,7 +674,6 @@ def _generate_conversation_turn(
                 conversation_id=conversation_id,
                 target_agent_message=target_agent_message,
                 contexts=contexts,
-                document=document,
             )
 
             return ConversationTurnCreateResponse(
@@ -776,54 +699,3 @@ def _get_conversation_message_from_conversation(
                         return message
 
         errors.raise_not_found_error(f"Could not retrieve {agent_type} agent message")
-
-    def _send_target_agent_message(
-        self,
-        target_agent: TargetAgent,
-        conversation_id: str,
-        agent_maihem_message: Optional[str] = None,
-    ) -> Tuple[str, List[str]]:
-        target_agent_message, contexts = target_agent._send_message(
-            conversation_id, agent_maihem_message
-        )
-
-        return target_agent_message, contexts
-
-
-class MaihemAsync(Client):
-
-    def __init__(self) -> None:
-        self.type = "async"
-
-    def create_target_agent(
-        self,
-        identifier: str,
-        role: str,
-        company: str,
-        industry: str,
-        description: str,
-    ) -> TargetAgent:
-        raise NotImplementedError("Method not implemented")
-
-    def get_target_agent(self, identifier: str) -> TargetAgent:
-        raise NotImplementedError("Method not implemented")
-
-    def create_test(
-        self,
-        test_identifier: str,
-        initiating_agent: Literal["maihem", "target"],
-        maihem_agent_behavior_prompt: str = None,
-        conversation_turns_max: int = 10,
-        metrics_config: Dict = None,
-    ) -> Test:
-        raise NotImplementedError("Method not implemented")
-
-    def create_test_run(
-        self,
-        identifier: str,
-        test_identifier: str,
-        target_agent: TargetAgent,
-        dynamic_mode: Literal["static", "dynamic"],
-        concurrent_conversations: int,
-    ) -> TestRun:
-        raise NotImplementedError("Method not implemented")
diff --git a/src/maihem/errors.py b/src/maihem/errors.py
index 881059d..3809182 100644
--- a/src/maihem/errors.py
+++ b/src/maihem/errors.py
@@ -13,7 +13,7 @@
 
 
 class ErrorCodes(str, Enum):
-    ERR_CHAT_FUNCTION = "err_chat_function"
+    ERR_WRAPPER_FUNCTION = "err_wrapper_function"
     ERR_CONFIG_FILE = "err_config_file"
     ERR_INTERNAL_SERVER = ErrorCodesAPI.ERR_INTERNAL_SERVER
     ERR_NOT_FOUND = ErrorCodesAPI.ERR_NOT_FOUND
@@ -63,10 +63,11 @@ def __init__(self, error_resp: ErrorResponse) -> None:
         super().__init__(error_resp)
 
 
-class ChatFunctionError(ErrorBase):
+class WrapperFunctionError(ErrorBase):
     def __init__(self, error_resp: ErrorResponse) -> None:
         super().__init__(error_resp)
-        
+
+
 class ConfigFileError(ErrorBase):
     def __init__(self, error_resp: ErrorResponse) -> None:
         super().__init__(error_resp)
@@ -131,17 +132,17 @@ def raise_not_found_error(message: str):
     )
 
 
-def raise_chat_function_error(message: str):
-    raise ChatFunctionError(
+def raise_wrapper_function_error(message: str):
+    raise WrapperFunctionError(
         ErrorResponse(
             error=ErrorResponseError(
-                code=ErrorCodes.ERR_CHAT_FUNCTION, message=message, detail=None
+                code=ErrorCodes.ERR_WRAPPER_FUNCTION, message=message, detail=None
             ),
             request_id=None,
         )
     )
-    
-    
+
+
 def raise_config_file_error(message: str):
     raise ConfigFileError(
         ErrorResponse(
diff --git a/src/maihem/image_parser.py b/src/maihem/image_parser.py
index 5303349..75464c5 100644
--- a/src/maihem/image_parser.py
+++ b/src/maihem/image_parser.py
@@ -1,5 +1,4 @@
 import pymupdf  # PyMuPDF
-from docx import Document
 from PIL import Image
 import io
 import os
diff --git a/src/maihem/modules_map.py b/src/maihem/modules_map.py
new file mode 100644
index 0000000..5804a66
--- /dev/null
+++ b/src/maihem/modules_map.py
@@ -0,0 +1,29 @@
+from typing import List, Dict, Any
+
+import maihem.errors as errors
+from maihem.utils.utils import spread_n_into_buckets
+
+
+def map_module_list_to_metrics(
+    modules: List[str], number_conversations: int
+) -> Dict[str, Dict[str, Any]]:
+    """Map modules to metrics."""
+    metrics_config = {}
+    for module in modules:
+        if module == "cx":
+            convs_list = spread_n_into_buckets(number_conversations, 4)
+            metrics_config["qa_cx_goal_completion"] = convs_list[0]
+            metrics_config["qa_cx_helpfulness"] = convs_list[1]
+            metrics_config["qa_cx_retention"] = convs_list[2]
+            metrics_config["qa_cx_nps"] = convs_list[3]
+        elif module == "rag":
+            convs_list = spread_n_into_buckets(number_conversations, 3)
+            metrics_config["qa_rag_hallucination"] = convs_list[0]
+            metrics_config["qa_rag_answer_relevance"] = convs_list[1]
+            metrics_config["qa_rag_context_relevance"] = convs_list[2]
+        else:
+            raise errors.raise_not_found_error(
+                f"Module '{module}' is not supported. Please check the supported modules in https://docs.maihem.ai/reference/metric-collection."
+            )
+
+    return metrics_config
diff --git a/src/maihem/schemas/agents.py b/src/maihem/schemas/agents.py
index fc7eda1..7f4a991 100644
--- a/src/maihem/schemas/agents.py
+++ b/src/maihem/schemas/agents.py
@@ -8,7 +8,8 @@
 
 import maihem.errors as errors
 from maihem.logger import get_logger
-from maihem.utils import extract_text
+
+logger = get_logger()
 
 
 class AgentType(str, Enum):
@@ -20,34 +21,29 @@ class TargetAgent(BaseModel):
     id: str
     created_at: datetime
     updated_at: datetime
-    identifier: str
-    name: Optional[str] = None
-    role: str
+    name: str
+    label: Optional[str] = None
+    role: Optional[str] = None
     description: Optional[str] = None
     industry: Optional[str] = None
     language: Optional[LanguageAlpha2] = "en"
 
-    _chat_function: Optional[Callable] = None
+    _wrapper_function: Optional[Callable] = None
     document_paths: List[str] = []
 
-    def set_chat_function(self, chat_function: Callable) -> None:
-        logger = get_logger()
-        is_test_success = self.test_chat_function(chat_function)
+    def set_wrapper_function(self, wrapper_function: Callable) -> None:
+        is_test_success = self.test_wrapper_function(wrapper_function)
 
         if is_test_success:
-            self._chat_function = chat_function
-            logger.info("Chat function tested and added successfully!")
+            self._wrapper_function = wrapper_function
+            logger.info("Wrapper function tested and added successfully")
 
-    def test_chat_function(self, chat_function: Callable) -> bool:
-        logger = get_logger()
+    def test_wrapper_function(self, wrapper_function: Callable) -> bool:
         test_message = "Hi, it's the Maihem agent. Ready for testing?"
-        logger.info("Testing chat function...")
-        logger.info(f"Sending chatbot message: {test_message}")
+        logger.info("Testing wrapper function...")
+        logger.info(f"Sending message to target agent: {test_message}")
         try:
-            message, contexts = chat_function(
-                str(datetime.now()),
-                test_message,
-            )
+            message, contexts = wrapper_function(str(datetime.now()), test_message, {})
             assert isinstance(message, str), "Response message must be a string"
             assert isinstance(contexts, list), "Contexts must be a list"
             for context in contexts:
@@ -57,12 +53,11 @@ def test_chat_function(self, chat_function: Callable) -> bool:
 
             return True
         except Exception as e:
-            errors.raise_chat_function_error(
-                f"Error testing target agent chat function: {e}"
+            errors.raise_wrapper_function_error(
+                f"Error testing target agent wrapper function: {e}"
             )
 
     def add_documents(self, documents: List[str]) -> None:
-        logger = get_logger()
         for doc_path in documents:
             if not os.path.exists(doc_path):
                 logger.warning(f"Document not found: {doc_path}")
@@ -88,9 +83,25 @@ def add_documents(self, documents: List[str]) -> None:
                 logger.error(f"Error processing document {doc_path}: {str(e)}")
 
     def _send_message(
-        self, conversation_id: str, message: Optional[str] = ""
+        self,
+        conversation_id: str,
+        message: Optional[str] = "",
+        conversation_history: Dict = {},
     ) -> Tuple[str, List[str]]:
-        if not self._chat_function:
-            errors.raise_chat_function_error("Target agent chat function not set")
-        response, contexts = self._chat_function(conversation_id, message)
-        return response, contexts
+        if not self._wrapper_function:
+            errors.raise_wrapper_function_error("Target agent wrapper function not set")
+        for retry in range(3):
+            try:
+                response, contexts = self._wrapper_function(
+                    conversation_id, message, conversation_history
+                )
+                return response, contexts
+            except Exception as e:
+                if retry < 2:
+                    logger.warning(
+                        f"Error sending message to target agent, retrying ({retry + 1}). Error: {str(e)}"
+                    )
+                else:
+                    errors.raise_wrapper_function_error(
+                        f"Error sending message to target agent after 3 retries. Error: {str(e)}"
+                    )
diff --git a/src/maihem/simulator.py b/src/maihem/simulator.py
deleted file mode 100644
index f864c5f..0000000
--- a/src/maihem/simulator.py
+++ /dev/null
@@ -1,195 +0,0 @@
-from typing import List, Callable, Dict
-import yaml
-
-from maihem.clients import Maihem
-from maihem.errors import raise_config_file_error
-from maihem.logger import get_logger
-from maihem.schemas.tests import SimulatedConversation
-
-
-class Simulator:
-    """
-    Class to simulate conversations between the Maihem Agent and the Target Agent
-    """
-
-    @classmethod
-    def conversation(
-        cls,
-        chat_function: Callable,
-        target_agent_identifier: str,
-        maihem_agent_identifier: str,
-        config_path: str = "./config.yaml",
-    ) -> SimulatedConversation:
-        """Simulate a single conversation between the Maihem Agent and the Target Agent"""
-        logger = get_logger()
-
-        # Read config.yaml file
-        config = cls._load_config(
-            config_path=config_path, 
-            target_agent_identifier=target_agent_identifier, 
-            identifier=maihem_agent_identifier,
-            dev_mode=True
-        )
-        
-        maihem_client = Maihem()
-        
-        logger.info("Initiating conversation...")
-        target_agent = maihem_client.upsert_target_agent(
-            identifier=target_agent_identifier,
-            role=config["target_agent"][target_agent_identifier]["role"],
-            industry=config["target_agent"][target_agent_identifier]["industry"],
-            description=config["target_agent"][target_agent_identifier]["description"],
-            name=config["target_agent"][target_agent_identifier]["name"],
-            language=config["target_agent"][target_agent_identifier]["language"],
-        )
-        target_agent.set_chat_function(chat_function)
-        
-        if (
-            "documents" in config["maihem_agent"][maihem_agent_identifier] and
-            len(config["maihem_agent"][maihem_agent_identifier]["documents"]) > 0 and
-            "rag" in config["maihem_agent"][maihem_agent_identifier]["metric"] 
-        ):
-            target_agent.add_documents(documents=config["maihem_agent"][maihem_agent_identifier]["documents"])
-        
-        metrics_config = {config["maihem_agent"][maihem_agent_identifier]["metric"]: 1}
-        
-        test = maihem_client.upsert_test(
-            identifier=maihem_agent_identifier,
-            initiating_agent=config["maihem_agent"][maihem_agent_identifier]["initiating_agent"],
-            name=config["maihem_agent"][maihem_agent_identifier]["name"],
-            maihem_agent_behavior_prompt=config["maihem_agent"][maihem_agent_identifier]["behavior_prompt"],
-            conversation_turns_max=config["maihem_agent"][maihem_agent_identifier]["conversation_turns_max"],
-            metrics_config=metrics_config,
-            target_agent_identifier=target_agent_identifier
-        )
-        
-        test_run = maihem_client.create_test_run_dev_mode(
-            test_identifier=test.identifier,
-            target_agent=target_agent
-        )
-        
-        conversations = maihem_client.get_test_run_result_conversations(test_run.id)
-        
-        return SimulatedConversation(conversations, 0)
-    
-    @classmethod
-    def test(
-        cls, 
-        chat_function: Callable,
-        target_agent_identifier: str,
-        test_identifier: str,      
-        config_path: str = "./config.yaml",    
-    ) -> SimulatedConversation:
-        """Simulate a single conversation between the Maihem Agent and the Target Agent"""
-        logger = get_logger()
-        
-        # Read config.yaml file
-        config = cls._load_config(
-            config_path=config_path, 
-            target_agent_identifier=target_agent_identifier,
-            identifier=test_identifier, 
-            dev_mode=False
-        )
-        
-        maihem_client = Maihem()
-
-        logger.info("Initiating conversation...")
-        target_agent = maihem_client.upsert_target_agent(
-            identifier=target_agent_identifier,
-            role=config["target_agent"][target_agent_identifier]["role"],
-            industry=config["target_agent"][target_agent_identifier]["industry"],
-            description=config["target_agent"][target_agent_identifier]["description"],
-            name=config["target_agent"][target_agent_identifier]["name"],
-            language=config["target_agent"][target_agent_identifier]["language"],
-        )
-        target_agent.set_chat_function(chat_function)
-
-        metrics_config = {metric: 10 for metric in config["test"][test_identifier]["metrics"]}
-
-        test = maihem_client.upsert_test(
-            identifier=test_identifier,
-            initiating_agent=config["test"][test_identifier]["initiating_agent"],
-            name=config["test"][test_identifier]["name"],
-            maihem_agent_behavior_prompt=config["test"][test_identifier]["behavior_prompt"],
-            conversation_turns_max=config["test"][test_identifier]["conversation_turns_max"],
-            metrics_config=metrics_config,
-            target_agent_identifier=target_agent_identifier
-        )
-
-        test_run = maihem_client.create_test_run(
-            test_identifier=test.identifier, 
-            target_agent=target_agent,
-            concurrent_conversations=len(config["test"][test_identifier]["metrics"])
-        )
-
-        conversations = maihem_client.get_test_run_result_conversations(test_run.id)
-        conversations_transformed = [SimulatedConversation(conversations, i) for i in range(len(conversations.conversations))]
-
-        return conversations_transformed
-
-    @classmethod
-    def _load_config(
-        cls, 
-        config_path: str, 
-        target_agent_identifier: str,
-        identifier: str,
-        dev_mode: bool = True
-    ) -> Dict:
-        logger = get_logger()
-        try:
-            with open(config_path, "r") as file:
-                config = yaml.safe_load(file)
-        except Exception as e:
-            logger.error(f"Error reading config file: {str(e)}")
-            raise_config_file_error(f"Error reading config file: {str(e)}")
-
-        try:
-            # Check if required keys for target agent are present in config file
-            assert "target_agent" in config, "'target_agent' key not found in config file"
-            assert target_agent_identifier in config["target_agent"].keys(), f"Target agent '{target_agent_identifier}' not found in config file"
-            
-            for tg_ag_identifier, target_agent in config["target_agent"].items():
-                assert "role" in target_agent, f"'role' key not found in target agent {tg_ag_identifier}"
-                assert "industry" in target_agent, f"'industry' key not found in target agent {tg_ag_identifier}"
-                assert "description" in target_agent, f"'description' key not found in target agent {tg_ag_identifier}"
-                target_agent["name"] = target_agent.get("name")
-                target_agent["language"] = target_agent.get("language")
-                
-                for key in target_agent.keys():
-                    if key not in ["name", "role", "industry", "description", "language"]:
-                        raise_config_file_error(f"Invalid key '{key}' found in target agent {identifier}")
-                       
-            if dev_mode:
-                assert "maihem_agent" in config, "'maihem_agent' key not found in config file" 
-                assert "metric" in config["maihem_agent"][identifier].keys(), f"'metric' key not found in {identifier}"
-                assert identifier in config["maihem_agent"].keys(), f"Maihem agent '{identifier}' not found in config file"
-            else:
-                assert "test" in config, "'test' key not found in config file" 
-                assert "metrics" in config["test"][identifier].keys(), f"'metrics' key not found in {identifier}"
-                assert identifier in config["test"].keys(), f"Test '{identifier}' not found in config file"
-            
-            instance_type = "maihem_agent" if dev_mode else "test"
-            for identifier, instance in config[instance_type].items():
-                instance["name"] = instance.get("name")
-                if dev_mode:
-                    instance["metric"] = instance.get("metric")
-                else:
-                    assert isinstance(instance["metrics"], list), f"'metrics' key must be a list in {identifier}"
-                    instance["metrics"] = instance.get("metrics")
-                    assert len(instance["metrics"]) > 0, f"'metrics' key must have at least one metric in {identifier}"
-                instance["behavior_prompt"] = instance.get("behavior_prompt")
-                instance["initiating_agent"] = instance.get("initiating_agent")
-                instance["conversation_turns_max"] = instance.get("conversation_turns_max")
-                if "documents" in instance.keys():
-                    instance["documents"] = instance.get("documents")
-                    assert isinstance(instance["documents"], list), f"'documents' key must be a list in {identifier}"
-                
-                for key in instance.keys():
-                    if key not in ["name", "metric", "metrics", "behavior_prompt", "initiating_agent", "conversation_turns_max", "documents"]:
-                        raise_config_file_error(f"Invalid key '{key}' found in {identifier}")
-
-        except Exception as e:
-            logger.error(f"Error reading config file: {str(e)}")
-            raise_config_file_error(f"Error reading config file: {str(e)}")
-        
-        return config 
diff --git a/src/maihem/utils.py b/src/maihem/utils/documents.py
similarity index 90%
rename from src/maihem/utils.py
rename to src/maihem/utils/documents.py
index 5f3bbb0..d89f076 100644
--- a/src/maihem/utils.py
+++ b/src/maihem/utils/documents.py
@@ -1,10 +1,27 @@
+import docx2txt
 import os
 import pymupdf
-import docx2txt
-
-from typing import List, Iterable, Optional
+from typing import List, Iterable, Optional, Dict
 import re
 
+from maihem.logger import get_logger
+
+logger = get_logger()
+
+
+def parse_documents(documents_path: str) -> Dict[str, str]:
+    """Parse documents from a directory and return a list of strings."""
+    documents = {}
+    for file in os.listdir(documents_path):
+        if (
+            file.endswith(".pdf")
+            or file.endswith(".docx")
+            or file.endswith(".txt")
+            or file.endswith(".md")
+        ):
+            documents[file] = extract_text(os.path.join(documents_path, file))
+    return documents
+
 
 def extract_text(file_path):
     file_extension = os.path.splitext(file_path)[1].lower()
diff --git a/src/maihem/utils/utils.py b/src/maihem/utils/utils.py
new file mode 100644
index 0000000..e25f95e
--- /dev/null
+++ b/src/maihem/utils/utils.py
@@ -0,0 +1,88 @@
+import importlib.util
+import os
+from typing import List, Callable
+
+import maihem.errors as errors
+from maihem.logger import get_logger
+
+logger = get_logger()
+
+
+def spread_n_into_buckets(n: int, buckets: int) -> List[int]:
+    if not isinstance(n, int) or not isinstance(buckets, int):
+        raise TypeError("n and buckets must be integers")
+    if n < 1 or buckets < 1:
+        raise ValueError("n and buckets must be greater than or equal to 1")
+
+    return [
+        max(1, n // buckets + (1 if x < n % buckets else 0)) for x in range(buckets)
+    ]
+
+
+def import_wrapper_function(path: str = "wrapper_function.py") -> Callable:
+    if not os.path.exists(path):
+        errors.raise_not_found_error(f"Wrapper function file not found at: {path}")
+
+    if not os.path.isfile(path):
+        errors.raise_not_found_error(f"Path exists but is not a file: {path}")
+
+    try:
+        spec = importlib.util.spec_from_file_location(
+            "wrapper_function", os.path.abspath(path)
+        )
+        if spec is None or spec.loader is None:
+            errors.raise_not_found_error("Failed to load module specification")
+
+        wrapper_module = importlib.util.module_from_spec(spec)
+        spec.loader.exec_module(wrapper_module)
+
+        if not hasattr(wrapper_module, "wrapper_function"):
+            errors.raise_not_found_error("Module does not contain 'wrapper_function'")
+
+        wrapper_function = wrapper_module.wrapper_function
+        return wrapper_function
+    except Exception as e:
+        errors.raise_not_found_error(
+            f"Wrapper function could not be imported. Error: {e}"
+        )
+
+
+def create_project_folder(name: str) -> None:
+    file_content = """import requests
+from typing import List, Tuple
+
+def wrapper_function(
+    conversation_id: str,
+    maihem_agent_message: str | None,
+    conversation_history: dict,
+) -> Tuple[str, List[str]]:
+    \"\"\"Callable function to wrap your target agent to be tested.\"\"\"
+    # Call demo Maihem target agent for quickstart
+    url = "https://demo-agent.maihem.ai/chat"
+    payload = {"message": maihem_agent_message if maihem_agent_message else " "}
+    response = requests.request("POST", url, json=payload).json()
+    return response["message"], response["contexts"]
+"""
+    if not name or not isinstance(name, str):
+        raise ValueError("Project name must be a non-empty string")
+
+    # Sanitize the folder name to prevent directory traversal
+    name = os.path.basename(name)
+
+    try:
+        os.makedirs(name, exist_ok=True, mode=0o755)  # Explicit permissions
+
+        file_path = os.path.join(name, "wrapper_function.py")
+
+        # Check if file already exists to prevent accidental overwrites
+        if os.path.exists(file_path):
+            logger.warning(f"File already exists at {file_path}")
+            return
+
+        with open(file_path, "w", encoding="utf-8") as file:
+            file.write(file_content)
+
+        logger.info(f"Project folder created: '{name}'")
+    except OSError as e:
+        logger.error(f"Failed to create project folder: {e}")
+        raise
diff --git a/src/maihem_config_dev_mode.yaml b/src/maihem_config_dev_mode.yaml
deleted file mode 100644
index 7f0bbe8..0000000
--- a/src/maihem_config_dev_mode.yaml
+++ /dev/null
@@ -1,17 +0,0 @@
-target_agent:
-  tg_ag_therapy_1: # Unique identifier for the target agent.
-    name: Acme Therapy Agent
-    role: mental health assistant
-    industry: mental health
-    description: A chatbot for emotional support through Cognitive Behavioral Therapy (CBT)
-    language: en  
-maihem_agent:
-  mh_ag_venting_1: # Unique identifier for the Maihem agent
-    name: Venting agent
-    metric: qa_rag_hallucination  # See list of supported metrics here: https://docs.maihem.ai/metrics/collection
-    behavior_prompt: Vent about stress caused by high demands in the workplace
-    initiating_agent: maihem  # maihem or target
-    conversation_turns_max: 4
-    # documents:  # (Optional) Load documents for RAG question generation
-    #   - /path_to_doc_1.pdf
-    #   - /path_to_doc_2.txt
diff --git a/src/run_maihem.py b/src/run_maihem.py
deleted file mode 100644
index f628dd5..0000000
--- a/src/run_maihem.py
+++ /dev/null
@@ -1,81 +0,0 @@
-import argparse
-import os
-from typing import List, Tuple
-from maihem import Simulator
-
-# Set the Maihem API key as an environment variable
-# os.environ['MAIHEM_API_KEY'] = '<YOUR_API_KEY>'
-
-parser = argparse.ArgumentParser()
-
-# Choose identifier of the target agent, to be defined in config.yaml
-parser.add_argument("--mode", default="dev", choices=["dev", "test"], type=str)
-
-# Choose identifier of the target agent, to be defined in config.yaml
-parser.add_argument("--target_agent_identifier", default="tg_ag_therapy_1", type=str)
-
-# Choose identifier of the maihem agent, to be defined in config.yaml
-parser.add_argument("--maihem_agent_identifier", default="mh_ag_venting_1", type=str)
-
-# Choose identifier of the test, to be defined in config.yaml
-parser.add_argument("--test_identifier", default="test_a", type=str)
-
-# Path to config.yaml
-parser.add_argument("--config_path", default="./src/config.yaml", type=str)
-
-
-# Example of chat function
-def chat_function(conversation_id: str, agent_maihem_message: str) -> Tuple[str, List[str]]:
-    """
-    Callable chat function to wrap your target agent to be tested.
-
-    params:
-    - conversation_id: unique conversation ID generated by Maihem, use it to keep track of different conversations
-    - agent_maihem_msg: message from the Maihem Agent
-
-    return:
-    - agent_target_message [str] - message from your Target Agent in response to the Maihem Agent message
-    - contexts [List[str]] - list of contexts (required for RAG evaluations), pass empty list if not needed
-    """
-    
-    # The message from your Target Agent. 
-    # Connect your agent here to respond to agent_maihem_message. 
-    # Keep track of same or new conversations with conversation_id
-    agent_target_message = "Hi, how can I help you today?"
-    
-    # List of contexts for RAG evaluations, pass empty list if not needed
-    contexts = ["Context 1", "Context 2"] 
-    # contexts = ["<Context 1>", "<Context 2>"] 
-    
-    # Delete when you have implemented your chat function
-    raise NotImplementedError("Chat function has not been implemented")
-    
-    return agent_target_message, contexts
-
-
-if __name__ == "__main__":
-    
-    if parser.parse_args().mode == "dev":
-        conversation = Simulator.conversation(
-            chat_function, 
-            target_agent_identifier=parser.parse_args().target_agent_identifier, 
-            maihem_agent_identifier=parser.parse_args().maihem_agent_identifier, 
-            config_path=parser.parse_args().config_path
-        )
-        
-        print(conversation.messages)
-        print(conversation.evaluation)
-        
-    elif parser.parse_args().mode == "test":  
-        conversations = Simulator.test(
-            chat_function, 
-            target_agent_identifier=parser.parse_args().target_agent_identifier, 
-            test_identifier=parser.parse_args().test_identifier, 
-            config_path=parser.parse_args().config_path
-        )
-        
-        print(conversations[0].messages)
-        print(conversations[0].evaluation)
-        
-    else:
-        raise ValueError("Invalid mode. Choose 'dev' or 'test'")


Test patch:
diff --git a/design_maihem_test.py b/design_maihem_test.py
deleted file mode 100644
index e699489..0000000
--- a/design_maihem_test.py
+++ /dev/null
@@ -1,73 +0,0 @@
-from typing import List, Tuple
-
-from maihem.clients import Maihem
-
-# Add API key to MAIHEM_API_KEY environment variable
-# os.environ["MAIHEM_API_KEY"] = api_key
-maihem_client = Maihem()
-
-target_agent = maihem_client.create_target_agent(
-    name="PG_Chatbot_1", # Name of the Target Agent, does not have to be unique
-    identifier="tg_ag_1234567", # (Optional) Define unique identifier for your Target Agent, or we create one for you
-    target_agent_role="mental health assistant",
-    target_agent_description="A chatbot for emotional support"
-)
-
-# or get target agent if it already exists
-target_agent = TargetAgent.get(identifier="id_1234567")
-
-# Example of chat function to call your Target Agent
-def chat_function(conversation_id: str, agent_maihem_message: str) -> Tuple[str, List[str]]:
-    """
-    Callable chat function to wrap your target agent to be tested.
-
-    params:
-    - conversation_id: unique conversation ID generated by Maihem, use it to keep track of different conversations
-    - agent_maihem_msg: message from the Maihem Agent
-
-    return:
-    - agent_target_message [str] - message from your Target Agent in response to the Maihem Agent message
-    - contexts [List[str]] - list of contexts (required for RAG evaluations), pass empty list if not needed
-    """
-    
-    # The message from your Target Agent. 
-    # Connect your agent here to respond to agent_maihem_message. 
-    # Keep track of same or new conversations with conversation_id
-    agent_target_message = "Hi, how can I help you today?"
-    
-    # List of contexts for RAG evaluations, pass empty list if not needed
-    contexts = ["<Context 1>", "<Context 2>"] 
-    
-    return agent_target_message, contexts
-    
-# Set the chat function to the Target Agent, so we can automatically chat with your Target Agent
-target_agent.set_chat_function(chat_function)
-
-# For RAG testing, add a list of documents so Maihem can generate questions from them to evaluate your Target Agent
-target_agent.add_documents(documents=["./test_data/RAG_PG_essays.pdf"])
-
-# Create a Test
-test = MaihemClient.create_test(
-    name="Test PG Essays", # Name of the Test, does not have to be unique
-    identifier="test_pg_essays_1234", # (Optional) Define unique identifier for the Test, or we create one for you
-    eval="helpfulness", # (Optional) Select metric to evaluate, default is "helpfulness"
-    workflow_prompt="Vent about stress in the workplace.", # (Optional) Guide the behavior of the Maihem Agent with a prompt describing the workflow of the user
-    workflow_dict={}, # (Optional) Provide a dictionary of the workflow to guide the behavior of the Maihem Agent, or use our tool to help you generate this
-    add_personality=True, # (Optional) Add personality to the agent
-    turns_max=10, # (Optional) Set maximum number of turns
-)
-
-# # Create a Test Run from a Test and a Target Agent
-test_run = MaihemClient.create_test_run(
-    test_identifier="test_pg_essays", # The identifier of the Test you want to run
-    target_agent=target_agent, # The Target Agent you want to test
-    concurrent_conversations=10, # How many conversations to run concurrently
-)
-
-# Get the results of the Test Run (status and how many conversations passed or failed)
-results = MaihemClient.get_test_run_result(test_run_id=test_run.id)
-print(results)
-
-# Get the conversations generated in the Test Run
-conversations = MaihemClient.get_test_run_result_conversations(test_run_id=test_run.id)
-print(conversations)
\ No newline at end of file
diff --git a/src/maihem/api_client/maihem_client/api/tests/tests_upsert_test.py b/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_create_test_result_metric_review.py
similarity index 68%
rename from src/maihem/api_client/maihem_client/api/tests/tests_upsert_test.py
rename to src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_create_test_result_metric_review.py
index 8f80a70..f7efca3 100644
--- a/src/maihem/api_client/maihem_client/api/tests/tests_upsert_test.py
+++ b/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_create_test_result_metric_review.py
@@ -5,15 +5,14 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test import APISchemaTest
-from ...models.api_schema_test_create_request import APISchemaTestCreateRequest
+from ...models.admin_test_result_metric_review_create_request import AdminTestResultMetricReviewCreateRequest
 from ...models.error_response import ErrorResponse
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     *,
-    body: APISchemaTestCreateRequest,
+    body: AdminTestResultMetricReviewCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -21,8 +20,8 @@ def _get_kwargs(
         headers["x-api-key"] = x_api_key
 
     _kwargs: Dict[str, Any] = {
-        "method": "put",
-        "url": "/tests",
+        "method": "post",
+        "url": "/admin/test-result-metrics/reviews",
     }
 
     _body = body.to_dict()
@@ -36,35 +35,30 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
-    if response.status_code == HTTPStatus.CREATED:
-        response_201 = APISchemaTest.from_dict(response.json())
-
+) -> Optional[Union[Any, ErrorResponse]]:
+    if response.status_code == 201:
+        response_201 = response.json()
         return response_201
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTest.from_dict(response.json())
-
-        return response_200
     if client.raise_on_unexpected_status:
         raise errors.UnexpectedStatus(response.status_code, response.content)
     else:
@@ -73,7 +67,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[Any, ErrorResponse]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -85,23 +79,23 @@ def _build_response(
 def sync_detailed(
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: AdminTestResultMetricReviewCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
-    """Upsert test by identifier
+) -> Response[Union[Any, ErrorResponse]]:
+    """Create an evaluation review
 
-     Create or update a test by identifier
+     Create an evaluation review
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (AdminTestResultMetricReviewCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTest, ErrorResponse]]
+        Response[Union[Any, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -119,23 +113,23 @@ def sync_detailed(
 def sync(
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: AdminTestResultMetricReviewCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
-    """Upsert test by identifier
+) -> Optional[Union[Any, ErrorResponse]]:
+    """Create an evaluation review
 
-     Create or update a test by identifier
+     Create an evaluation review
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (AdminTestResultMetricReviewCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTest, ErrorResponse]
+        Union[Any, ErrorResponse]
     """
 
     return sync_detailed(
@@ -148,23 +142,23 @@ def sync(
 async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: AdminTestResultMetricReviewCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
-    """Upsert test by identifier
+) -> Response[Union[Any, ErrorResponse]]:
+    """Create an evaluation review
 
-     Create or update a test by identifier
+     Create an evaluation review
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (AdminTestResultMetricReviewCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTest, ErrorResponse]]
+        Response[Union[Any, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -180,23 +174,23 @@ async def asyncio_detailed(
 async def asyncio(
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: AdminTestResultMetricReviewCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
-    """Upsert test by identifier
+) -> Optional[Union[Any, ErrorResponse]]:
+    """Create an evaluation review
 
-     Create or update a test by identifier
+     Create an evaluation review
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (AdminTestResultMetricReviewCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTest, ErrorResponse]
+        Union[Any, ErrorResponse]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/agents/agents_upsert_agent_target.py b/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_edit_test_result_metric.py
similarity index 65%
rename from src/maihem/api_client/maihem_client/api/agents/agents_upsert_agent_target.py
rename to src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_edit_test_result_metric.py
index d3c193a..f87123b 100644
--- a/src/maihem/api_client/maihem_client/api/agents/agents_upsert_agent_target.py
+++ b/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_edit_test_result_metric.py
@@ -5,15 +5,14 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_agent_target import APISchemaAgentTarget
-from ...models.api_schema_agent_target_create_request import APISchemaAgentTargetCreateRequest
+from ...models.admin_test_result_metric_review_edit_request import AdminTestResultMetricReviewEditRequest
 from ...models.error_response import ErrorResponse
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     *,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AdminTestResultMetricReviewEditRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -21,8 +20,8 @@ def _get_kwargs(
         headers["x-api-key"] = x_api_key
 
     _kwargs: Dict[str, Any] = {
-        "method": "put",
-        "url": "/agents/target",
+        "method": "patch",
+        "url": "/admin/test-result-metrics",
     }
 
     _body = body.to_dict()
@@ -36,35 +35,30 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
-    if response.status_code == HTTPStatus.CREATED:
-        response_201 = APISchemaAgentTarget.from_dict(response.json())
-
-        return response_201
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+) -> Optional[Union[Any, ErrorResponse]]:
+    if response.status_code == 200:
+        response_200 = response.json()
+        return response_200
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaAgentTarget.from_dict(response.json())
-
-        return response_200
     if client.raise_on_unexpected_status:
         raise errors.UnexpectedStatus(response.status_code, response.content)
     else:
@@ -73,7 +67,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
+) -> Response[Union[Any, ErrorResponse]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -85,23 +79,23 @@ def _build_response(
 def sync_detailed(
     *,
     client: AuthenticatedClient,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AdminTestResultMetricReviewEditRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
-    """Upsert target agent by identifier
+) -> Response[Union[Any, ErrorResponse]]:
+    """Edit evaluation
 
-     Create or update a target agent by identifier
+     Edit an evaluation
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaAgentTargetCreateRequest):
+        body (AdminTestResultMetricReviewEditRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaAgentTarget, ErrorResponse]]
+        Response[Union[Any, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -119,23 +113,23 @@ def sync_detailed(
 def sync(
     *,
     client: AuthenticatedClient,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AdminTestResultMetricReviewEditRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
-    """Upsert target agent by identifier
+) -> Optional[Union[Any, ErrorResponse]]:
+    """Edit evaluation
 
-     Create or update a target agent by identifier
+     Edit an evaluation
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaAgentTargetCreateRequest):
+        body (AdminTestResultMetricReviewEditRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaAgentTarget, ErrorResponse]
+        Union[Any, ErrorResponse]
     """
 
     return sync_detailed(
@@ -148,23 +142,23 @@ def sync(
 async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AdminTestResultMetricReviewEditRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaAgentTarget, ErrorResponse]]:
-    """Upsert target agent by identifier
+) -> Response[Union[Any, ErrorResponse]]:
+    """Edit evaluation
 
-     Create or update a target agent by identifier
+     Edit an evaluation
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaAgentTargetCreateRequest):
+        body (AdminTestResultMetricReviewEditRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaAgentTarget, ErrorResponse]]
+        Response[Union[Any, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -180,23 +174,23 @@ async def asyncio_detailed(
 async def asyncio(
     *,
     client: AuthenticatedClient,
-    body: APISchemaAgentTargetCreateRequest,
+    body: AdminTestResultMetricReviewEditRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaAgentTarget, ErrorResponse]]:
-    """Upsert target agent by identifier
+) -> Optional[Union[Any, ErrorResponse]]:
+    """Edit evaluation
 
-     Create or update a target agent by identifier
+     Edit an evaluation
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaAgentTargetCreateRequest):
+        body (AdminTestResultMetricReviewEditRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaAgentTarget, ErrorResponse]
+        Union[Any, ErrorResponse]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_get_test_result_metric_review_audits.py b/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_get_test_result_metric_review_audits.py
new file mode 100644
index 0000000..14eda7f
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_get_test_result_metric_review_audits.py
@@ -0,0 +1,216 @@
+from http import HTTPStatus
+from typing import Any, Dict, List, Optional, Union
+
+import httpx
+
+from ... import errors
+from ...client import AuthenticatedClient, Client
+from ...models.error_response import ErrorResponse
+from ...models.v_test_result_metric_review_audit import VTestResultMetricReviewAudit
+from ...types import UNSET, Response, Unset
+
+
+def _get_kwargs(
+    test_run_id: str,
+    metric_id: str,
+    *,
+    x_api_key: Union[None, Unset, str] = UNSET,
+) -> Dict[str, Any]:
+    headers: Dict[str, Any] = {}
+    if not isinstance(x_api_key, Unset):
+        headers["x-api-key"] = x_api_key
+
+    _kwargs: Dict[str, Any] = {
+        "method": "get",
+        "url": f"/admin/test-runs/{test_run_id}/metrics/{metric_id}/test-result-metrics/reviews/audits",
+    }
+
+    _kwargs["headers"] = headers
+    return _kwargs
+
+
+def _parse_response(
+    *, client: Union[AuthenticatedClient, Client], response: httpx.Response
+) -> Optional[Union[ErrorResponse, List["VTestResultMetricReviewAudit"]]]:
+    if response.status_code == 200:
+        response_200 = []
+        _response_200 = response.json()
+        for response_200_item_data in _response_200:
+            response_200_item = VTestResultMetricReviewAudit.from_dict(response_200_item_data)
+
+            response_200.append(response_200_item)
+
+        return response_200
+    if response.status_code == 400:
+        response_400 = ErrorResponse.from_dict(response.json())
+
+        return response_400
+    if response.status_code == 409:
+        response_409 = ErrorResponse.from_dict(response.json())
+
+        return response_409
+    if response.status_code == 422:
+        response_422 = ErrorResponse.from_dict(response.json())
+
+        return response_422
+    if response.status_code == 500:
+        response_500 = ErrorResponse.from_dict(response.json())
+
+        return response_500
+    if response.status_code == 504:
+        response_504 = ErrorResponse.from_dict(response.json())
+
+        return response_504
+    if client.raise_on_unexpected_status:
+        raise errors.UnexpectedStatus(response.status_code, response.content)
+    else:
+        return None
+
+
+def _build_response(
+    *, client: Union[AuthenticatedClient, Client], response: httpx.Response
+) -> Response[Union[ErrorResponse, List["VTestResultMetricReviewAudit"]]]:
+    return Response(
+        status_code=HTTPStatus(response.status_code),
+        content=response.content,
+        headers=response.headers,
+        parsed=_parse_response(client=client, response=response),
+    )
+
+
+def sync_detailed(
+    test_run_id: str,
+    metric_id: str,
+    *,
+    client: AuthenticatedClient,
+    x_api_key: Union[None, Unset, str] = UNSET,
+) -> Response[Union[ErrorResponse, List["VTestResultMetricReviewAudit"]]]:
+    """Get evaluation review audit history
+
+     Get evaluation review audit history
+
+    Args:
+        test_run_id (str):
+        metric_id (str):
+        x_api_key (Union[None, Unset, str]):
+
+    Raises:
+        errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
+        httpx.TimeoutException: If the request takes longer than Client.timeout.
+
+    Returns:
+        Response[Union[ErrorResponse, List['VTestResultMetricReviewAudit']]]
+    """
+
+    kwargs = _get_kwargs(
+        test_run_id=test_run_id,
+        metric_id=metric_id,
+        x_api_key=x_api_key,
+    )
+
+    response = client.get_httpx_client().request(
+        **kwargs,
+    )
+
+    return _build_response(client=client, response=response)
+
+
+def sync(
+    test_run_id: str,
+    metric_id: str,
+    *,
+    client: AuthenticatedClient,
+    x_api_key: Union[None, Unset, str] = UNSET,
+) -> Optional[Union[ErrorResponse, List["VTestResultMetricReviewAudit"]]]:
+    """Get evaluation review audit history
+
+     Get evaluation review audit history
+
+    Args:
+        test_run_id (str):
+        metric_id (str):
+        x_api_key (Union[None, Unset, str]):
+
+    Raises:
+        errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
+        httpx.TimeoutException: If the request takes longer than Client.timeout.
+
+    Returns:
+        Union[ErrorResponse, List['VTestResultMetricReviewAudit']]
+    """
+
+    return sync_detailed(
+        test_run_id=test_run_id,
+        metric_id=metric_id,
+        client=client,
+        x_api_key=x_api_key,
+    ).parsed
+
+
+async def asyncio_detailed(
+    test_run_id: str,
+    metric_id: str,
+    *,
+    client: AuthenticatedClient,
+    x_api_key: Union[None, Unset, str] = UNSET,
+) -> Response[Union[ErrorResponse, List["VTestResultMetricReviewAudit"]]]:
+    """Get evaluation review audit history
+
+     Get evaluation review audit history
+
+    Args:
+        test_run_id (str):
+        metric_id (str):
+        x_api_key (Union[None, Unset, str]):
+
+    Raises:
+        errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
+        httpx.TimeoutException: If the request takes longer than Client.timeout.
+
+    Returns:
+        Response[Union[ErrorResponse, List['VTestResultMetricReviewAudit']]]
+    """
+
+    kwargs = _get_kwargs(
+        test_run_id=test_run_id,
+        metric_id=metric_id,
+        x_api_key=x_api_key,
+    )
+
+    response = await client.get_async_httpx_client().request(**kwargs)
+
+    return _build_response(client=client, response=response)
+
+
+async def asyncio(
+    test_run_id: str,
+    metric_id: str,
+    *,
+    client: AuthenticatedClient,
+    x_api_key: Union[None, Unset, str] = UNSET,
+) -> Optional[Union[ErrorResponse, List["VTestResultMetricReviewAudit"]]]:
+    """Get evaluation review audit history
+
+     Get evaluation review audit history
+
+    Args:
+        test_run_id (str):
+        metric_id (str):
+        x_api_key (Union[None, Unset, str]):
+
+    Raises:
+        errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
+        httpx.TimeoutException: If the request takes longer than Client.timeout.
+
+    Returns:
+        Union[ErrorResponse, List['VTestResultMetricReviewAudit']]
+    """
+
+    return (
+        await asyncio_detailed(
+            test_run_id=test_run_id,
+            metric_id=metric_id,
+            client=client,
+            x_api_key=x_api_key,
+        )
+    ).parsed
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result_with_metric_conversations.py b/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_get_test_result_metric_review_states.py
similarity index 71%
rename from src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result_with_metric_conversations.py
rename to src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_get_test_result_metric_review_states.py
index dbad144..ba7dddd 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result_with_metric_conversations.py
+++ b/src/maihem/api_client/maihem_client/api/admin_internal/admin_internal_admin_get_test_result_metric_review_states.py
@@ -1,12 +1,12 @@
 from http import HTTPStatus
-from typing import Any, Dict, Optional, Union
+from typing import Any, Dict, List, Optional, Union
 
 import httpx
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run_result_conversations import APISchemaTestRunResultConversations
 from ...models.error_response import ErrorResponse
+from ...models.v_test_result_metric_review_state import VTestResultMetricReviewState
 from ...types import UNSET, Response, Unset
 
 
@@ -22,7 +22,7 @@ def _get_kwargs(
 
     _kwargs: Dict[str, Any] = {
         "method": "get",
-        "url": f"/test-runs/{test_run_id}/results/metrics/{metric_id}/conversations",
+        "url": f"/admin/test-runs/{test_run_id}/metrics/{metric_id}/test-result-metrics/reviews/states",
     }
 
     _kwargs["headers"] = headers
@@ -31,28 +31,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTestRunResultConversations.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, List["VTestResultMetricReviewState"]]]:
+    if response.status_code == 200:
+        response_200 = []
+        _response_200 = response.json()
+        for response_200_item_data in _response_200:
+            response_200_item = VTestResultMetricReviewState.from_dict(response_200_item_data)
+
+            response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -64,7 +69,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, List["VTestResultMetricReviewState"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -79,10 +84,10 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
-    """Get test run result metric conversations
+) -> Response[Union[ErrorResponse, List["VTestResultMetricReviewState"]]]:
+    """Get evaluation review states
 
-     Get a test run result with metric conversations
+     Get evaluation review states
 
     Args:
         test_run_id (str):
@@ -94,7 +99,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]
+        Response[Union[ErrorResponse, List['VTestResultMetricReviewState']]]
     """
 
     kwargs = _get_kwargs(
@@ -116,10 +121,10 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
-    """Get test run result metric conversations
+) -> Optional[Union[ErrorResponse, List["VTestResultMetricReviewState"]]]:
+    """Get evaluation review states
 
-     Get a test run result with metric conversations
+     Get evaluation review states
 
     Args:
         test_run_id (str):
@@ -131,7 +136,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRunResultConversations, ErrorResponse]
+        Union[ErrorResponse, List['VTestResultMetricReviewState']]
     """
 
     return sync_detailed(
@@ -148,10 +153,10 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
-    """Get test run result metric conversations
+) -> Response[Union[ErrorResponse, List["VTestResultMetricReviewState"]]]:
+    """Get evaluation review states
 
-     Get a test run result with metric conversations
+     Get evaluation review states
 
     Args:
         test_run_id (str):
@@ -163,7 +168,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]
+        Response[Union[ErrorResponse, List['VTestResultMetricReviewState']]]
     """
 
     kwargs = _get_kwargs(
@@ -183,10 +188,10 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
-    """Get test run result metric conversations
+) -> Optional[Union[ErrorResponse, List["VTestResultMetricReviewState"]]]:
+    """Get evaluation review states
 
-     Get a test run result with metric conversations
+     Get evaluation review states
 
     Args:
         test_run_id (str):
@@ -198,7 +203,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRunResultConversations, ErrorResponse]
+        Union[ErrorResponse, List['VTestResultMetricReviewState']]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/test_result_metrics/test_result_metrics_add_test_result_metric_feedback.py b/src/maihem/api_client/maihem_client/api/test_result_metrics/test_result_metrics_add_test_result_metric_feedback.py
index ab7abc0..2e1f28b 100644
--- a/src/maihem/api_client/maihem_client/api/test_result_metrics/test_result_metrics_add_test_result_metric_feedback.py
+++ b/src/maihem/api_client/maihem_client/api/test_result_metrics/test_result_metrics_add_test_result_metric_feedback.py
@@ -5,18 +5,15 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_result_metric_feedback import APISchemaTestResultMetricFeedback
-from ...models.api_schema_test_result_metric_feedback_create_request import (
-    APISchemaTestResultMetricFeedbackCreateRequest,
-)
 from ...models.error_response import ErrorResponse
+from ...models.test_result_metric_feedback import TestResultMetricFeedback
+from ...models.test_result_metric_feedback_create_request import TestResultMetricFeedbackCreateRequest
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
-    trm_id: str,
     *,
-    body: APISchemaTestResultMetricFeedbackCreateRequest,
+    body: TestResultMetricFeedbackCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -25,7 +22,7 @@ def _get_kwargs(
 
     _kwargs: Dict[str, Any] = {
         "method": "post",
-        "url": f"/test-result-metrics/{trm_id}/feedback",
+        "url": "/test-result-metrics/feedback",
     }
 
     _body = body.to_dict()
@@ -39,28 +36,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTestResultMetricFeedback, ErrorResponse]]:
-    if response.status_code == HTTPStatus.CREATED:
-        response_201 = APISchemaTestResultMetricFeedback.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, TestResultMetricFeedback]]:
+    if response.status_code == 201:
+        response_201 = TestResultMetricFeedback.from_dict(response.json())
 
         return response_201
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -72,7 +69,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTestResultMetricFeedback, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestResultMetricFeedback]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -82,31 +79,28 @@ def _build_response(
 
 
 def sync_detailed(
-    trm_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestResultMetricFeedbackCreateRequest,
+    body: TestResultMetricFeedbackCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestResultMetricFeedback, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestResultMetricFeedback]]:
     """Add test result metric feedback
 
      Add feedback to a test result metric
 
     Args:
-        trm_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestResultMetricFeedbackCreateRequest):
+        body (TestResultMetricFeedbackCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestResultMetricFeedback, ErrorResponse]]
+        Response[Union[ErrorResponse, TestResultMetricFeedback]]
     """
 
     kwargs = _get_kwargs(
-        trm_id=trm_id,
         body=body,
         x_api_key=x_api_key,
     )
@@ -119,31 +113,28 @@ def sync_detailed(
 
 
 def sync(
-    trm_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestResultMetricFeedbackCreateRequest,
+    body: TestResultMetricFeedbackCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestResultMetricFeedback, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestResultMetricFeedback]]:
     """Add test result metric feedback
 
      Add feedback to a test result metric
 
     Args:
-        trm_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestResultMetricFeedbackCreateRequest):
+        body (TestResultMetricFeedbackCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestResultMetricFeedback, ErrorResponse]
+        Union[ErrorResponse, TestResultMetricFeedback]
     """
 
     return sync_detailed(
-        trm_id=trm_id,
         client=client,
         body=body,
         x_api_key=x_api_key,
@@ -151,31 +142,28 @@ def sync(
 
 
 async def asyncio_detailed(
-    trm_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestResultMetricFeedbackCreateRequest,
+    body: TestResultMetricFeedbackCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestResultMetricFeedback, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestResultMetricFeedback]]:
     """Add test result metric feedback
 
      Add feedback to a test result metric
 
     Args:
-        trm_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestResultMetricFeedbackCreateRequest):
+        body (TestResultMetricFeedbackCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestResultMetricFeedback, ErrorResponse]]
+        Response[Union[ErrorResponse, TestResultMetricFeedback]]
     """
 
     kwargs = _get_kwargs(
-        trm_id=trm_id,
         body=body,
         x_api_key=x_api_key,
     )
@@ -186,32 +174,29 @@ async def asyncio_detailed(
 
 
 async def asyncio(
-    trm_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestResultMetricFeedbackCreateRequest,
+    body: TestResultMetricFeedbackCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestResultMetricFeedback, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestResultMetricFeedback]]:
     """Add test result metric feedback
 
      Add feedback to a test result metric
 
     Args:
-        trm_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestResultMetricFeedbackCreateRequest):
+        body (TestResultMetricFeedbackCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestResultMetricFeedback, ErrorResponse]
+        Union[ErrorResponse, TestResultMetricFeedback]
     """
 
     return (
         await asyncio_detailed(
-            trm_id=trm_id,
             client=client,
             body=body,
             x_api_key=x_api_key,
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_create_conversation_turn.py b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_create_conversation_turn.py
index 7efadb9..8a5cb0e 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_create_conversation_turn.py
+++ b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_create_conversation_turn.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_conversation_turn_create_request import APISchemaConversationTurnCreateRequest
-from ...models.api_schema_conversation_turn_create_response import APISchemaConversationTurnCreateResponse
+from ...models.conversation_turn_create_request import ConversationTurnCreateRequest
+from ...models.conversation_turn_create_response import ConversationTurnCreateResponse
 from ...models.error_response import ErrorResponse
 from ...types import UNSET, Response, Unset
 
@@ -15,7 +15,7 @@ def _get_kwargs(
     test_run_id: str,
     conversation_id: str,
     *,
-    body: APISchemaConversationTurnCreateRequest,
+    body: ConversationTurnCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -38,28 +38,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaConversationTurnCreateResponse, ErrorResponse]]:
-    if response.status_code == HTTPStatus.CREATED:
-        response_201 = APISchemaConversationTurnCreateResponse.from_dict(response.json())
+) -> Optional[Union[ConversationTurnCreateResponse, ErrorResponse]]:
+    if response.status_code == 201:
+        response_201 = ConversationTurnCreateResponse.from_dict(response.json())
 
         return response_201
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -71,7 +71,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaConversationTurnCreateResponse, ErrorResponse]]:
+) -> Response[Union[ConversationTurnCreateResponse, ErrorResponse]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -85,9 +85,9 @@ def sync_detailed(
     conversation_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaConversationTurnCreateRequest,
+    body: ConversationTurnCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaConversationTurnCreateResponse, ErrorResponse]]:
+) -> Response[Union[ConversationTurnCreateResponse, ErrorResponse]]:
     """Create a conversation turn
 
      Create a new turn in a specified conversation
@@ -96,14 +96,14 @@ def sync_detailed(
         test_run_id (str):
         conversation_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaConversationTurnCreateRequest):
+        body (ConversationTurnCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaConversationTurnCreateResponse, ErrorResponse]]
+        Response[Union[ConversationTurnCreateResponse, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -125,9 +125,9 @@ def sync(
     conversation_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaConversationTurnCreateRequest,
+    body: ConversationTurnCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaConversationTurnCreateResponse, ErrorResponse]]:
+) -> Optional[Union[ConversationTurnCreateResponse, ErrorResponse]]:
     """Create a conversation turn
 
      Create a new turn in a specified conversation
@@ -136,14 +136,14 @@ def sync(
         test_run_id (str):
         conversation_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaConversationTurnCreateRequest):
+        body (ConversationTurnCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaConversationTurnCreateResponse, ErrorResponse]
+        Union[ConversationTurnCreateResponse, ErrorResponse]
     """
 
     return sync_detailed(
@@ -160,9 +160,9 @@ async def asyncio_detailed(
     conversation_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaConversationTurnCreateRequest,
+    body: ConversationTurnCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaConversationTurnCreateResponse, ErrorResponse]]:
+) -> Response[Union[ConversationTurnCreateResponse, ErrorResponse]]:
     """Create a conversation turn
 
      Create a new turn in a specified conversation
@@ -171,14 +171,14 @@ async def asyncio_detailed(
         test_run_id (str):
         conversation_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaConversationTurnCreateRequest):
+        body (ConversationTurnCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaConversationTurnCreateResponse, ErrorResponse]]
+        Response[Union[ConversationTurnCreateResponse, ErrorResponse]]
     """
 
     kwargs = _get_kwargs(
@@ -198,9 +198,9 @@ async def asyncio(
     conversation_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaConversationTurnCreateRequest,
+    body: ConversationTurnCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaConversationTurnCreateResponse, ErrorResponse]]:
+) -> Optional[Union[ConversationTurnCreateResponse, ErrorResponse]]:
     """Create a conversation turn
 
      Create a new turn in a specified conversation
@@ -209,14 +209,14 @@ async def asyncio(
         test_run_id (str):
         conversation_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaConversationTurnCreateRequest):
+        body (ConversationTurnCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaConversationTurnCreateResponse, ErrorResponse]
+        Union[ConversationTurnCreateResponse, ErrorResponse]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run.py b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run.py
index 1048315..681980e 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run.py
+++ b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run import APISchemaTestRun
 from ...models.error_response import ErrorResponse
+from ...models.test_run import TestRun
 from ...types import UNSET, Response, Unset
 
 
@@ -30,28 +30,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTestRun.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, TestRun]]:
+    if response.status_code == 200:
+        response_200 = TestRun.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -63,7 +63,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -77,7 +77,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     """Get a test run
 
      Get a specified test run
@@ -91,7 +91,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRun, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRun]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRun]]:
     """Get a test run
 
      Get a specified test run
@@ -125,7 +125,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRun, ErrorResponse]
+        Union[ErrorResponse, TestRun]
     """
 
     return sync_detailed(
@@ -140,7 +140,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     """Get a test run
 
      Get a specified test run
@@ -154,7 +154,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRun, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRun]]
     """
 
     kwargs = _get_kwargs(
@@ -172,7 +172,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRun]]:
     """Get a test run
 
      Get a specified test run
@@ -186,7 +186,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRun, ErrorResponse]
+        Union[ErrorResponse, TestRun]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_conversations.py b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_conversations.py
index 63348be..dbecedd 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_conversations.py
+++ b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_conversations.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run_conversations import APISchemaTestRunConversations
 from ...models.error_response import ErrorResponse
+from ...models.test_run_conversation_i_ds import TestRunConversationIDs
 from ...types import UNSET, Response, Unset
 
 
@@ -30,28 +30,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTestRunConversations, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTestRunConversations.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, TestRunConversationIDs]]:
+    if response.status_code == 200:
+        response_200 = TestRunConversationIDs.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -63,7 +63,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTestRunConversations, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunConversationIDs]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -77,10 +77,10 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRunConversations, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunConversationIDs]]:
     """Get test run conversations
 
-     Get a test run result including conversations to be run
+     Get a test run including conversations to be run
 
     Args:
         test_run_id (str):
@@ -91,7 +91,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRunConversations, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRunConversationIDs]]
     """
 
     kwargs = _get_kwargs(
@@ -111,10 +111,10 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRunConversations, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRunConversationIDs]]:
     """Get test run conversations
 
-     Get a test run result including conversations to be run
+     Get a test run including conversations to be run
 
     Args:
         test_run_id (str):
@@ -125,7 +125,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRunConversations, ErrorResponse]
+        Union[ErrorResponse, TestRunConversationIDs]
     """
 
     return sync_detailed(
@@ -140,10 +140,10 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRunConversations, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunConversationIDs]]:
     """Get test run conversations
 
-     Get a test run result including conversations to be run
+     Get a test run including conversations to be run
 
     Args:
         test_run_id (str):
@@ -154,7 +154,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRunConversations, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRunConversationIDs]]
     """
 
     kwargs = _get_kwargs(
@@ -172,10 +172,10 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRunConversations, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRunConversationIDs]]:
     """Get test run conversations
 
-     Get a test run result including conversations to be run
+     Get a test run including conversations to be run
 
     Args:
         test_run_id (str):
@@ -186,7 +186,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRunConversations, ErrorResponse]
+        Union[ErrorResponse, TestRunConversationIDs]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result.py b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result.py
index b94abbc..9ca5612 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result.py
+++ b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run_result_metrics import APISchemaTestRunResultMetrics
 from ...models.error_response import ErrorResponse
+from ...models.test_run_results import TestRunResults
 from ...types import UNSET, Response, Unset
 
 
@@ -30,28 +30,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTestRunResultMetrics, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTestRunResultMetrics.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, TestRunResults]]:
+    if response.status_code == 200:
+        response_200 = TestRunResults.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -63,7 +63,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTestRunResultMetrics, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunResults]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -77,7 +77,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRunResultMetrics, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunResults]]:
     """Get test run results
 
      Get test run results
@@ -91,7 +91,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRunResultMetrics, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRunResults]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRunResultMetrics, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRunResults]]:
     """Get test run results
 
      Get test run results
@@ -125,7 +125,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRunResultMetrics, ErrorResponse]
+        Union[ErrorResponse, TestRunResults]
     """
 
     return sync_detailed(
@@ -140,7 +140,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRunResultMetrics, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunResults]]:
     """Get test run results
 
      Get test run results
@@ -154,7 +154,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRunResultMetrics, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRunResults]]
     """
 
     kwargs = _get_kwargs(
@@ -172,7 +172,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRunResultMetrics, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRunResults]]:
     """Get test run results
 
      Get test run results
@@ -186,7 +186,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRunResultMetrics, ErrorResponse]
+        Union[ErrorResponse, TestRunResults]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result_with_conversations.py b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result_with_conversations.py
index 7de337e..ac3bac4 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result_with_conversations.py
+++ b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_result_with_conversations.py
@@ -5,23 +5,44 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run_result_conversations import APISchemaTestRunResultConversations
 from ...models.error_response import ErrorResponse
+from ...models.test_run_results_conversations import TestRunResultsConversations
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     test_run_id: str,
     *,
+    metric_id: Union[None, Unset, str] = UNSET,
+    metric_result: Union[None, Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
     if not isinstance(x_api_key, Unset):
         headers["x-api-key"] = x_api_key
 
+    params: Dict[str, Any] = {}
+
+    json_metric_id: Union[None, Unset, str]
+    if isinstance(metric_id, Unset):
+        json_metric_id = UNSET
+    else:
+        json_metric_id = metric_id
+    params["metric_id"] = json_metric_id
+
+    json_metric_result: Union[None, Unset, str]
+    if isinstance(metric_result, Unset):
+        json_metric_result = UNSET
+    else:
+        json_metric_result = metric_result
+    params["metric_result"] = json_metric_result
+
+    params = {k: v for k, v in params.items() if v is not UNSET and v is not None}
+
     _kwargs: Dict[str, Any] = {
         "method": "get",
         "url": f"/test-runs/{test_run_id}/results/conversations",
+        "params": params,
     }
 
     _kwargs["headers"] = headers
@@ -30,28 +51,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTestRunResultConversations.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, TestRunResultsConversations]]:
+    if response.status_code == 200:
+        response_200 = TestRunResultsConversations.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -63,7 +84,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunResultsConversations]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -76,14 +97,18 @@ def sync_detailed(
     test_run_id: str,
     *,
     client: AuthenticatedClient,
+    metric_id: Union[None, Unset, str] = UNSET,
+    metric_result: Union[None, Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunResultsConversations]]:
     """Get test run result with conversations
 
      Get a test run result including agent conversations
 
     Args:
         test_run_id (str):
+        metric_id (Union[None, Unset, str]):
+        metric_result (Union[None, Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -91,11 +116,13 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRunResultsConversations]]
     """
 
     kwargs = _get_kwargs(
         test_run_id=test_run_id,
+        metric_id=metric_id,
+        metric_result=metric_result,
         x_api_key=x_api_key,
     )
 
@@ -110,14 +137,18 @@ def sync(
     test_run_id: str,
     *,
     client: AuthenticatedClient,
+    metric_id: Union[None, Unset, str] = UNSET,
+    metric_result: Union[None, Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRunResultsConversations]]:
     """Get test run result with conversations
 
      Get a test run result including agent conversations
 
     Args:
         test_run_id (str):
+        metric_id (Union[None, Unset, str]):
+        metric_result (Union[None, Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -125,12 +156,14 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRunResultConversations, ErrorResponse]
+        Union[ErrorResponse, TestRunResultsConversations]
     """
 
     return sync_detailed(
         test_run_id=test_run_id,
         client=client,
+        metric_id=metric_id,
+        metric_result=metric_result,
         x_api_key=x_api_key,
     ).parsed
 
@@ -139,14 +172,18 @@ async def asyncio_detailed(
     test_run_id: str,
     *,
     client: AuthenticatedClient,
+    metric_id: Union[None, Unset, str] = UNSET,
+    metric_result: Union[None, Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRunResultsConversations]]:
     """Get test run result with conversations
 
      Get a test run result including agent conversations
 
     Args:
         test_run_id (str):
+        metric_id (Union[None, Unset, str]):
+        metric_result (Union[None, Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -154,11 +191,13 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRunResultConversations, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRunResultsConversations]]
     """
 
     kwargs = _get_kwargs(
         test_run_id=test_run_id,
+        metric_id=metric_id,
+        metric_result=metric_result,
         x_api_key=x_api_key,
     )
 
@@ -171,14 +210,18 @@ async def asyncio(
     test_run_id: str,
     *,
     client: AuthenticatedClient,
+    metric_id: Union[None, Unset, str] = UNSET,
+    metric_result: Union[None, Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRunResultConversations, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRunResultsConversations]]:
     """Get test run result with conversations
 
      Get a test run result including agent conversations
 
     Args:
         test_run_id (str):
+        metric_id (Union[None, Unset, str]):
+        metric_result (Union[None, Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -186,13 +229,15 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRunResultConversations, ErrorResponse]
+        Union[ErrorResponse, TestRunResultsConversations]
     """
 
     return (
         await asyncio_detailed(
             test_run_id=test_run_id,
             client=client,
+            metric_id=metric_id,
+            metric_result=metric_result,
             x_api_key=x_api_key,
         )
     ).parsed
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_results.py b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_results.py
index f4d4fd0..9629b97 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_results.py
+++ b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_run_results.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run_result_metrics import APISchemaTestRunResultMetrics
 from ...models.error_response import ErrorResponse
+from ...models.test_run_results import TestRunResults
 from ...types import UNSET, Response, Unset
 
 
@@ -29,33 +29,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["TestRunResults"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaTestRunResultMetrics.from_dict(response_200_item_data)
+            response_200_item = TestRunResults.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -67,7 +67,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["TestRunResults"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -80,7 +80,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["TestRunResults"]]]:
     """Get all test run results
 
      Get all test test run results
@@ -93,7 +93,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTestRunResultMetrics']]]
+        Response[Union[ErrorResponse, List['TestRunResults']]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Optional[Union[ErrorResponse, List["TestRunResults"]]]:
     """Get all test run results
 
      Get all test test run results
@@ -124,7 +124,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTestRunResultMetrics']]
+        Union[ErrorResponse, List['TestRunResults']]
     """
 
     return sync_detailed(
@@ -137,7 +137,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["TestRunResults"]]]:
     """Get all test run results
 
      Get all test test run results
@@ -150,7 +150,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTestRunResultMetrics']]]
+        Response[Union[ErrorResponse, List['TestRunResults']]]
     """
 
     kwargs = _get_kwargs(
@@ -166,7 +166,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Optional[Union[ErrorResponse, List["TestRunResults"]]]:
     """Get all test run results
 
      Get all test test run results
@@ -179,7 +179,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTestRunResultMetrics']]
+        Union[ErrorResponse, List['TestRunResults']]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_runs.py b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_runs.py
index 9c492c0..08f0259 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_runs.py
+++ b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_get_test_runs.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run import APISchemaTestRun
 from ...models.error_response import ErrorResponse
+from ...models.test_run import TestRun
 from ...types import UNSET, Response, Unset
 
 
@@ -29,33 +29,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRun"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["TestRun"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaTestRun.from_dict(response_200_item_data)
+            response_200_item = TestRun.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -67,7 +67,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Response[Union[ErrorResponse, List["TestRun"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -80,7 +80,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Response[Union[ErrorResponse, List["TestRun"]]]:
     """Get all test runs
 
      Get a list of all test runs
@@ -93,7 +93,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTestRun']]]
+        Response[Union[ErrorResponse, List['TestRun']]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Optional[Union[ErrorResponse, List["TestRun"]]]:
     """Get all test runs
 
      Get a list of all test runs
@@ -124,7 +124,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTestRun']]
+        Union[ErrorResponse, List['TestRun']]
     """
 
     return sync_detailed(
@@ -137,7 +137,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Response[Union[ErrorResponse, List["TestRun"]]]:
     """Get all test runs
 
      Get a list of all test runs
@@ -150,7 +150,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTestRun']]]
+        Response[Union[ErrorResponse, List['TestRun']]]
     """
 
     kwargs = _get_kwargs(
@@ -166,7 +166,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Optional[Union[ErrorResponse, List["TestRun"]]]:
     """Get all test runs
 
      Get a list of all test runs
@@ -179,7 +179,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTestRun']]
+        Union[ErrorResponse, List['TestRun']]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_update_test_run_status.py b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_update_test_run_status.py
index 50cc3c7..f701dac 100644
--- a/src/maihem/api_client/maihem_client/api/test_runs/test_runs_update_test_run_status.py
+++ b/src/maihem/api_client/maihem_client/api/test_runs/test_runs_update_test_run_status.py
@@ -5,16 +5,16 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run import APISchemaTestRun
-from ...models.api_schema_test_run_status_update_request import APISchemaTestRunStatusUpdateRequest
 from ...models.error_response import ErrorResponse
+from ...models.test_run import TestRun
+from ...models.test_run_status_update_request import TestRunStatusUpdateRequest
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     test_run_id: str,
     *,
-    body: APISchemaTestRunStatusUpdateRequest,
+    body: TestRunStatusUpdateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -37,28 +37,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTestRun.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, TestRun]]:
+    if response.status_code == 200:
+        response_200 = TestRun.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -70,7 +70,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -83,9 +83,9 @@ def sync_detailed(
     test_run_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestRunStatusUpdateRequest,
+    body: TestRunStatusUpdateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     """Update test run status
 
      Update the status of a test run
@@ -93,14 +93,14 @@ def sync_detailed(
     Args:
         test_run_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestRunStatusUpdateRequest):
+        body (TestRunStatusUpdateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRun, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRun]]
     """
 
     kwargs = _get_kwargs(
@@ -120,9 +120,9 @@ def sync(
     test_run_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestRunStatusUpdateRequest,
+    body: TestRunStatusUpdateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRun]]:
     """Update test run status
 
      Update the status of a test run
@@ -130,14 +130,14 @@ def sync(
     Args:
         test_run_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestRunStatusUpdateRequest):
+        body (TestRunStatusUpdateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRun, ErrorResponse]
+        Union[ErrorResponse, TestRun]
     """
 
     return sync_detailed(
@@ -152,9 +152,9 @@ async def asyncio_detailed(
     test_run_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestRunStatusUpdateRequest,
+    body: TestRunStatusUpdateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     """Update test run status
 
      Update the status of a test run
@@ -162,14 +162,14 @@ async def asyncio_detailed(
     Args:
         test_run_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestRunStatusUpdateRequest):
+        body (TestRunStatusUpdateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRun, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRun]]
     """
 
     kwargs = _get_kwargs(
@@ -187,9 +187,9 @@ async def asyncio(
     test_run_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestRunStatusUpdateRequest,
+    body: TestRunStatusUpdateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRun]]:
     """Update test run status
 
      Update the status of a test run
@@ -197,14 +197,14 @@ async def asyncio(
     Args:
         test_run_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestRunStatusUpdateRequest):
+        body (TestRunStatusUpdateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRun, ErrorResponse]
+        Union[ErrorResponse, TestRun]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/tests/tests_create_test.py b/src/maihem/api_client/maihem_client/api/tests/tests_create_test.py
index 88b383c..6b276a6 100644
--- a/src/maihem/api_client/maihem_client/api/tests/tests_create_test.py
+++ b/src/maihem/api_client/maihem_client/api/tests/tests_create_test.py
@@ -5,15 +5,15 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test import APISchemaTest
-from ...models.api_schema_test_create_request import APISchemaTestCreateRequest
 from ...models.error_response import ErrorResponse
+from ...models.test import Test
+from ...models.test_create_request import TestCreateRequest
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     *,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -36,28 +36,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
-    if response.status_code == HTTPStatus.CREATED:
-        response_201 = APISchemaTest.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, Test]]:
+    if response.status_code == 201:
+        response_201 = Test.from_dict(response.json())
 
         return response_201
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -69,7 +69,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -81,23 +81,23 @@ def _build_response(
 def sync_detailed(
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     """Create test
 
      Create a new test configuration
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (TestCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTest, ErrorResponse]]
+        Response[Union[ErrorResponse, Test]]
     """
 
     kwargs = _get_kwargs(
@@ -115,23 +115,23 @@ def sync_detailed(
 def sync(
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, Test]]:
     """Create test
 
      Create a new test configuration
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (TestCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTest, ErrorResponse]
+        Union[ErrorResponse, Test]
     """
 
     return sync_detailed(
@@ -144,23 +144,23 @@ def sync(
 async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     """Create test
 
      Create a new test configuration
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (TestCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTest, ErrorResponse]]
+        Response[Union[ErrorResponse, Test]]
     """
 
     kwargs = _get_kwargs(
@@ -176,23 +176,23 @@ async def asyncio_detailed(
 async def asyncio(
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, Test]]:
     """Create test
 
      Create a new test configuration
 
     Args:
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (TestCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTest, ErrorResponse]
+        Union[ErrorResponse, Test]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/tests/tests_create_test_run.py b/src/maihem/api_client/maihem_client/api/tests/tests_create_test_run.py
index f09b7e8..bc8bdf7 100644
--- a/src/maihem/api_client/maihem_client/api/tests/tests_create_test_run.py
+++ b/src/maihem/api_client/maihem_client/api/tests/tests_create_test_run.py
@@ -5,14 +5,16 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run import APISchemaTestRun
+from ...models.create_test_run_request import CreateTestRunRequest
 from ...models.error_response import ErrorResponse
+from ...models.test_run import TestRun
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     test_id: str,
     *,
+    body: CreateTestRunRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -24,34 +26,39 @@ def _get_kwargs(
         "url": f"/tests/{test_id}/test-runs",
     }
 
+    _body = body.to_dict()
+
+    _kwargs["json"] = _body
+    headers["Content-Type"] = "application/json"
+
     _kwargs["headers"] = headers
     return _kwargs
 
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
-    if response.status_code == HTTPStatus.CREATED:
-        response_201 = APISchemaTestRun.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, TestRun]]:
+    if response.status_code == 201:
+        response_201 = TestRun.from_dict(response.json())
 
         return response_201
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -63,7 +70,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -76,8 +83,9 @@ def sync_detailed(
     test_id: str,
     *,
     client: AuthenticatedClient,
+    body: CreateTestRunRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     """Run a test
 
      Create a new run of a specified test
@@ -85,17 +93,19 @@ def sync_detailed(
     Args:
         test_id (str):
         x_api_key (Union[None, Unset, str]):
+        body (CreateTestRunRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRun, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRun]]
     """
 
     kwargs = _get_kwargs(
         test_id=test_id,
+        body=body,
         x_api_key=x_api_key,
     )
 
@@ -110,8 +120,9 @@ def sync(
     test_id: str,
     *,
     client: AuthenticatedClient,
+    body: CreateTestRunRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRun]]:
     """Run a test
 
      Create a new run of a specified test
@@ -119,18 +130,20 @@ def sync(
     Args:
         test_id (str):
         x_api_key (Union[None, Unset, str]):
+        body (CreateTestRunRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRun, ErrorResponse]
+        Union[ErrorResponse, TestRun]
     """
 
     return sync_detailed(
         test_id=test_id,
         client=client,
+        body=body,
         x_api_key=x_api_key,
     ).parsed
 
@@ -139,8 +152,9 @@ async def asyncio_detailed(
     test_id: str,
     *,
     client: AuthenticatedClient,
+    body: CreateTestRunRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, TestRun]]:
     """Run a test
 
      Create a new run of a specified test
@@ -148,17 +162,19 @@ async def asyncio_detailed(
     Args:
         test_id (str):
         x_api_key (Union[None, Unset, str]):
+        body (CreateTestRunRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTestRun, ErrorResponse]]
+        Response[Union[ErrorResponse, TestRun]]
     """
 
     kwargs = _get_kwargs(
         test_id=test_id,
+        body=body,
         x_api_key=x_api_key,
     )
 
@@ -171,8 +187,9 @@ async def asyncio(
     test_id: str,
     *,
     client: AuthenticatedClient,
+    body: CreateTestRunRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTestRun, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, TestRun]]:
     """Run a test
 
      Create a new run of a specified test
@@ -180,19 +197,21 @@ async def asyncio(
     Args:
         test_id (str):
         x_api_key (Union[None, Unset, str]):
+        body (CreateTestRunRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTestRun, ErrorResponse]
+        Union[ErrorResponse, TestRun]
     """
 
     return (
         await asyncio_detailed(
             test_id=test_id,
             client=client,
+            body=body,
             x_api_key=x_api_key,
         )
     ).parsed
diff --git a/src/maihem/api_client/maihem_client/api/tests/tests_get_test.py b/src/maihem/api_client/maihem_client/api/tests/tests_get_test.py
index 61bde8f..abd5b52 100644
--- a/src/maihem/api_client/maihem_client/api/tests/tests_get_test.py
+++ b/src/maihem/api_client/maihem_client/api/tests/tests_get_test.py
@@ -5,8 +5,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test import APISchemaTest
 from ...models.error_response import ErrorResponse
+from ...models.test import Test
 from ...types import UNSET, Response, Unset
 
 
@@ -30,28 +30,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTest.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, Test]]:
+    if response.status_code == 200:
+        response_200 = Test.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -63,7 +63,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -77,7 +77,7 @@ def sync_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     """Get test
 
      Gets a specified test
@@ -91,7 +91,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTest, ErrorResponse]]
+        Response[Union[ErrorResponse, Test]]
     """
 
     kwargs = _get_kwargs(
@@ -111,7 +111,7 @@ def sync(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, Test]]:
     """Get test
 
      Gets a specified test
@@ -125,7 +125,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTest, ErrorResponse]
+        Union[ErrorResponse, Test]
     """
 
     return sync_detailed(
@@ -140,7 +140,7 @@ async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     """Get test
 
      Gets a specified test
@@ -154,7 +154,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTest, ErrorResponse]]
+        Response[Union[ErrorResponse, Test]]
     """
 
     kwargs = _get_kwargs(
@@ -172,7 +172,7 @@ async def asyncio(
     *,
     client: AuthenticatedClient,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, Test]]:
     """Get test
 
      Gets a specified test
@@ -186,7 +186,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTest, ErrorResponse]
+        Union[ErrorResponse, Test]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/tests/tests_get_test_test_run_results.py b/src/maihem/api_client/maihem_client/api/tests/tests_get_test_test_run_results.py
index 06a1c30..594145f 100644
--- a/src/maihem/api_client/maihem_client/api/tests/tests_get_test_test_run_results.py
+++ b/src/maihem/api_client/maihem_client/api/tests/tests_get_test_test_run_results.py
@@ -6,8 +6,8 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run_result_metrics import APISchemaTestRunResultMetrics
 from ...models.error_response import ErrorResponse
+from ...models.test_run_results import TestRunResults
 from ...types import UNSET, Response, Unset
 
 
@@ -54,33 +54,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["TestRunResults"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaTestRunResultMetrics.from_dict(response_200_item_data)
+            response_200_item = TestRunResults.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -92,7 +92,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["TestRunResults"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -108,7 +108,7 @@ def sync_detailed(
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["TestRunResults"]]]:
     """Get all test run results for a test
 
      Get all test test run results for a test
@@ -124,7 +124,7 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTestRunResultMetrics']]]
+        Response[Union[ErrorResponse, List['TestRunResults']]]
     """
 
     kwargs = _get_kwargs(
@@ -148,7 +148,7 @@ def sync(
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Optional[Union[ErrorResponse, List["TestRunResults"]]]:
     """Get all test run results for a test
 
      Get all test test run results for a test
@@ -164,7 +164,7 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTestRunResultMetrics']]
+        Union[ErrorResponse, List['TestRunResults']]
     """
 
     return sync_detailed(
@@ -183,7 +183,7 @@ async def asyncio_detailed(
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Response[Union[ErrorResponse, List["TestRunResults"]]]:
     """Get all test run results for a test
 
      Get all test test run results for a test
@@ -199,7 +199,7 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTestRunResultMetrics']]]
+        Response[Union[ErrorResponse, List['TestRunResults']]]
     """
 
     kwargs = _get_kwargs(
@@ -221,7 +221,7 @@ async def asyncio(
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRunResultMetrics"]]]:
+) -> Optional[Union[ErrorResponse, List["TestRunResults"]]]:
     """Get all test run results for a test
 
      Get all test test run results for a test
@@ -237,7 +237,7 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTestRunResultMetrics']]
+        Union[ErrorResponse, List['TestRunResults']]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/api/tests/tests_get_test_test_runs.py b/src/maihem/api_client/maihem_client/api/tests/tests_get_test_test_runs.py
index 05edb23..ad71dda 100644
--- a/src/maihem/api_client/maihem_client/api/tests/tests_get_test_test_runs.py
+++ b/src/maihem/api_client/maihem_client/api/tests/tests_get_test_test_runs.py
@@ -6,14 +6,15 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test_run import APISchemaTestRun
 from ...models.error_response import ErrorResponse
+from ...models.test_run import TestRun
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     test_id: str,
     *,
+    name: Union[None, Unset, str] = UNSET,
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
@@ -24,6 +25,13 @@ def _get_kwargs(
 
     params: Dict[str, Any] = {}
 
+    json_name: Union[None, Unset, str]
+    if isinstance(name, Unset):
+        json_name = UNSET
+    else:
+        json_name = name
+    params["name"] = json_name
+
     json_before_datetime: Union[None, Unset, str]
     if isinstance(before_datetime, Unset):
         json_before_datetime = UNSET
@@ -54,33 +62,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRun"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["TestRun"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaTestRun.from_dict(response_200_item_data)
+            response_200_item = TestRun.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -92,7 +100,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Response[Union[ErrorResponse, List["TestRun"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -105,16 +113,18 @@ def sync_detailed(
     test_id: str,
     *,
     client: AuthenticatedClient,
+    name: Union[None, Unset, str] = UNSET,
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Response[Union[ErrorResponse, List["TestRun"]]]:
     """Get all test runs for a test
 
      Get a list of all test runs for a specified test
 
     Args:
         test_id (str):
+        name (Union[None, Unset, str]):
         before_datetime (Union[None, Unset, datetime.datetime]):
         limit (Union[None, Unset, int]):
         x_api_key (Union[None, Unset, str]):
@@ -124,11 +134,12 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTestRun']]]
+        Response[Union[ErrorResponse, List['TestRun']]]
     """
 
     kwargs = _get_kwargs(
         test_id=test_id,
+        name=name,
         before_datetime=before_datetime,
         limit=limit,
         x_api_key=x_api_key,
@@ -145,16 +156,18 @@ def sync(
     test_id: str,
     *,
     client: AuthenticatedClient,
+    name: Union[None, Unset, str] = UNSET,
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Optional[Union[ErrorResponse, List["TestRun"]]]:
     """Get all test runs for a test
 
      Get a list of all test runs for a specified test
 
     Args:
         test_id (str):
+        name (Union[None, Unset, str]):
         before_datetime (Union[None, Unset, datetime.datetime]):
         limit (Union[None, Unset, int]):
         x_api_key (Union[None, Unset, str]):
@@ -164,12 +177,13 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTestRun']]
+        Union[ErrorResponse, List['TestRun']]
     """
 
     return sync_detailed(
         test_id=test_id,
         client=client,
+        name=name,
         before_datetime=before_datetime,
         limit=limit,
         x_api_key=x_api_key,
@@ -180,16 +194,18 @@ async def asyncio_detailed(
     test_id: str,
     *,
     client: AuthenticatedClient,
+    name: Union[None, Unset, str] = UNSET,
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Response[Union[ErrorResponse, List["TestRun"]]]:
     """Get all test runs for a test
 
      Get a list of all test runs for a specified test
 
     Args:
         test_id (str):
+        name (Union[None, Unset, str]):
         before_datetime (Union[None, Unset, datetime.datetime]):
         limit (Union[None, Unset, int]):
         x_api_key (Union[None, Unset, str]):
@@ -199,11 +215,12 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTestRun']]]
+        Response[Union[ErrorResponse, List['TestRun']]]
     """
 
     kwargs = _get_kwargs(
         test_id=test_id,
+        name=name,
         before_datetime=before_datetime,
         limit=limit,
         x_api_key=x_api_key,
@@ -218,16 +235,18 @@ async def asyncio(
     test_id: str,
     *,
     client: AuthenticatedClient,
+    name: Union[None, Unset, str] = UNSET,
     before_datetime: Union[None, Unset, datetime.datetime] = UNSET,
     limit: Union[None, Unset, int] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTestRun"]]]:
+) -> Optional[Union[ErrorResponse, List["TestRun"]]]:
     """Get all test runs for a test
 
      Get a list of all test runs for a specified test
 
     Args:
         test_id (str):
+        name (Union[None, Unset, str]):
         before_datetime (Union[None, Unset, datetime.datetime]):
         limit (Union[None, Unset, int]):
         x_api_key (Union[None, Unset, str]):
@@ -237,13 +256,14 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTestRun']]
+        Union[ErrorResponse, List['TestRun']]
     """
 
     return (
         await asyncio_detailed(
             test_id=test_id,
             client=client,
+            name=name,
             before_datetime=before_datetime,
             limit=limit,
             x_api_key=x_api_key,
diff --git a/src/maihem/api_client/maihem_client/api/tests/tests_get_tests.py b/src/maihem/api_client/maihem_client/api/tests/tests_get_tests.py
index ec73b0e..e6c1e20 100644
--- a/src/maihem/api_client/maihem_client/api/tests/tests_get_tests.py
+++ b/src/maihem/api_client/maihem_client/api/tests/tests_get_tests.py
@@ -5,14 +5,14 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test import APISchemaTest
 from ...models.error_response import ErrorResponse
+from ...models.test import Test
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     *,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -21,7 +21,7 @@ def _get_kwargs(
 
     params: Dict[str, Any] = {}
 
-    params["identifier"] = identifier
+    params["name"] = name
 
     params = {k: v for k, v in params.items() if v is not UNSET and v is not None}
 
@@ -37,33 +37,33 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[ErrorResponse, List["APISchemaTest"]]]:
-    if response.status_code == HTTPStatus.OK:
+) -> Optional[Union[ErrorResponse, List["Test"]]]:
+    if response.status_code == 200:
         response_200 = []
         _response_200 = response.json()
         for response_200_item_data in _response_200:
-            response_200_item = APISchemaTest.from_dict(response_200_item_data)
+            response_200_item = Test.from_dict(response_200_item_data)
 
             response_200.append(response_200_item)
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -75,7 +75,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[ErrorResponse, List["APISchemaTest"]]]:
+) -> Response[Union[ErrorResponse, List["Test"]]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -87,15 +87,15 @@ def _build_response(
 def sync_detailed(
     *,
     client: AuthenticatedClient,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTest"]]]:
+) -> Response[Union[ErrorResponse, List["Test"]]]:
     """Get all tests
 
      Gets a list of all tests
 
     Args:
-        identifier (Union[Unset, str]):
+        name (Union[Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -103,11 +103,11 @@ def sync_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTest']]]
+        Response[Union[ErrorResponse, List['Test']]]
     """
 
     kwargs = _get_kwargs(
-        identifier=identifier,
+        name=name,
         x_api_key=x_api_key,
     )
 
@@ -121,15 +121,15 @@ def sync_detailed(
 def sync(
     *,
     client: AuthenticatedClient,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTest"]]]:
+) -> Optional[Union[ErrorResponse, List["Test"]]]:
     """Get all tests
 
      Gets a list of all tests
 
     Args:
-        identifier (Union[Unset, str]):
+        name (Union[Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -137,12 +137,12 @@ def sync(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTest']]
+        Union[ErrorResponse, List['Test']]
     """
 
     return sync_detailed(
         client=client,
-        identifier=identifier,
+        name=name,
         x_api_key=x_api_key,
     ).parsed
 
@@ -150,15 +150,15 @@ def sync(
 async def asyncio_detailed(
     *,
     client: AuthenticatedClient,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[ErrorResponse, List["APISchemaTest"]]]:
+) -> Response[Union[ErrorResponse, List["Test"]]]:
     """Get all tests
 
      Gets a list of all tests
 
     Args:
-        identifier (Union[Unset, str]):
+        name (Union[Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -166,11 +166,11 @@ async def asyncio_detailed(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[ErrorResponse, List['APISchemaTest']]]
+        Response[Union[ErrorResponse, List['Test']]]
     """
 
     kwargs = _get_kwargs(
-        identifier=identifier,
+        name=name,
         x_api_key=x_api_key,
     )
 
@@ -182,15 +182,15 @@ async def asyncio_detailed(
 async def asyncio(
     *,
     client: AuthenticatedClient,
-    identifier: Union[Unset, str] = UNSET,
+    name: Union[Unset, str] = UNSET,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[ErrorResponse, List["APISchemaTest"]]]:
+) -> Optional[Union[ErrorResponse, List["Test"]]]:
     """Get all tests
 
      Gets a list of all tests
 
     Args:
-        identifier (Union[Unset, str]):
+        name (Union[Unset, str]):
         x_api_key (Union[None, Unset, str]):
 
     Raises:
@@ -198,13 +198,13 @@ async def asyncio(
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[ErrorResponse, List['APISchemaTest']]
+        Union[ErrorResponse, List['Test']]
     """
 
     return (
         await asyncio_detailed(
             client=client,
-            identifier=identifier,
+            name=name,
             x_api_key=x_api_key,
         )
     ).parsed
diff --git a/src/maihem/api_client/maihem_client/api/tests/tests_update_test.py b/src/maihem/api_client/maihem_client/api/tests/tests_update_test.py
index bc2fa46..bae066e 100644
--- a/src/maihem/api_client/maihem_client/api/tests/tests_update_test.py
+++ b/src/maihem/api_client/maihem_client/api/tests/tests_update_test.py
@@ -5,16 +5,16 @@
 
 from ... import errors
 from ...client import AuthenticatedClient, Client
-from ...models.api_schema_test import APISchemaTest
-from ...models.api_schema_test_create_request import APISchemaTestCreateRequest
 from ...models.error_response import ErrorResponse
+from ...models.test import Test
+from ...models.test_create_request import TestCreateRequest
 from ...types import UNSET, Response, Unset
 
 
 def _get_kwargs(
     test_id: str,
     *,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
 ) -> Dict[str, Any]:
     headers: Dict[str, Any] = {}
@@ -37,28 +37,28 @@ def _get_kwargs(
 
 def _parse_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
-    if response.status_code == HTTPStatus.OK:
-        response_200 = APISchemaTest.from_dict(response.json())
+) -> Optional[Union[ErrorResponse, Test]]:
+    if response.status_code == 200:
+        response_200 = Test.from_dict(response.json())
 
         return response_200
-    if response.status_code == HTTPStatus.BAD_REQUEST:
+    if response.status_code == 400:
         response_400 = ErrorResponse.from_dict(response.json())
 
         return response_400
-    if response.status_code == HTTPStatus.CONFLICT:
+    if response.status_code == 409:
         response_409 = ErrorResponse.from_dict(response.json())
 
         return response_409
-    if response.status_code == HTTPStatus.UNPROCESSABLE_ENTITY:
+    if response.status_code == 422:
         response_422 = ErrorResponse.from_dict(response.json())
 
         return response_422
-    if response.status_code == HTTPStatus.INTERNAL_SERVER_ERROR:
+    if response.status_code == 500:
         response_500 = ErrorResponse.from_dict(response.json())
 
         return response_500
-    if response.status_code == HTTPStatus.GATEWAY_TIMEOUT:
+    if response.status_code == 504:
         response_504 = ErrorResponse.from_dict(response.json())
 
         return response_504
@@ -70,7 +70,7 @@ def _parse_response(
 
 def _build_response(
     *, client: Union[AuthenticatedClient, Client], response: httpx.Response
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     return Response(
         status_code=HTTPStatus(response.status_code),
         content=response.content,
@@ -83,9 +83,9 @@ def sync_detailed(
     test_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     """Update test
 
      Update a test configuration
@@ -93,14 +93,14 @@ def sync_detailed(
     Args:
         test_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (TestCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTest, ErrorResponse]]
+        Response[Union[ErrorResponse, Test]]
     """
 
     kwargs = _get_kwargs(
@@ -120,9 +120,9 @@ def sync(
     test_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, Test]]:
     """Update test
 
      Update a test configuration
@@ -130,14 +130,14 @@ def sync(
     Args:
         test_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (TestCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTest, ErrorResponse]
+        Union[ErrorResponse, Test]
     """
 
     return sync_detailed(
@@ -152,9 +152,9 @@ async def asyncio_detailed(
     test_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Response[Union[APISchemaTest, ErrorResponse]]:
+) -> Response[Union[ErrorResponse, Test]]:
     """Update test
 
      Update a test configuration
@@ -162,14 +162,14 @@ async def asyncio_detailed(
     Args:
         test_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (TestCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Response[Union[APISchemaTest, ErrorResponse]]
+        Response[Union[ErrorResponse, Test]]
     """
 
     kwargs = _get_kwargs(
@@ -187,9 +187,9 @@ async def asyncio(
     test_id: str,
     *,
     client: AuthenticatedClient,
-    body: APISchemaTestCreateRequest,
+    body: TestCreateRequest,
     x_api_key: Union[None, Unset, str] = UNSET,
-) -> Optional[Union[APISchemaTest, ErrorResponse]]:
+) -> Optional[Union[ErrorResponse, Test]]:
     """Update test
 
      Update a test configuration
@@ -197,14 +197,14 @@ async def asyncio(
     Args:
         test_id (str):
         x_api_key (Union[None, Unset, str]):
-        body (APISchemaTestCreateRequest):
+        body (TestCreateRequest):
 
     Raises:
         errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
         httpx.TimeoutException: If the request takes longer than Client.timeout.
 
     Returns:
-        Union[APISchemaTest, ErrorResponse]
+        Union[ErrorResponse, Test]
     """
 
     return (
diff --git a/src/maihem/api_client/maihem_client/models/admin_test_result_metric_review_create_request.py b/src/maihem/api_client/maihem_client/models/admin_test_result_metric_review_create_request.py
new file mode 100644
index 0000000..c35977a
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/admin_test_result_metric_review_create_request.py
@@ -0,0 +1,125 @@
+from typing import Any, Dict, List, Type, TypeVar, Union, cast
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+from ..types import UNSET, Unset
+
+T = TypeVar("T", bound="AdminTestResultMetricReviewCreateRequest")
+
+
+@_attrs_define
+class AdminTestResultMetricReviewCreateRequest:
+    """
+    Attributes:
+        entity_id (str):
+        entity_type (str):
+        action (str):
+        test_result_metric_id (Union[None, Unset, str]):
+        event (Union[Unset, str]):  Default: 'added'.
+        content (Union[None, Unset, str]):
+    """
+
+    entity_id: str
+    entity_type: str
+    action: str
+    test_result_metric_id: Union[None, Unset, str] = UNSET
+    event: Union[Unset, str] = "added"
+    content: Union[None, Unset, str] = UNSET
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        entity_id = self.entity_id
+
+        entity_type = self.entity_type
+
+        action = self.action
+
+        test_result_metric_id: Union[None, Unset, str]
+        if isinstance(self.test_result_metric_id, Unset):
+            test_result_metric_id = UNSET
+        else:
+            test_result_metric_id = self.test_result_metric_id
+
+        event = self.event
+
+        content: Union[None, Unset, str]
+        if isinstance(self.content, Unset):
+            content = UNSET
+        else:
+            content = self.content
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "entity_id": entity_id,
+                "entity_type": entity_type,
+                "action": action,
+            }
+        )
+        if test_result_metric_id is not UNSET:
+            field_dict["test_result_metric_id"] = test_result_metric_id
+        if event is not UNSET:
+            field_dict["event"] = event
+        if content is not UNSET:
+            field_dict["content"] = content
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        d = src_dict.copy()
+        entity_id = d.pop("entity_id")
+
+        entity_type = d.pop("entity_type")
+
+        action = d.pop("action")
+
+        def _parse_test_result_metric_id(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        test_result_metric_id = _parse_test_result_metric_id(d.pop("test_result_metric_id", UNSET))
+
+        event = d.pop("event", UNSET)
+
+        def _parse_content(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        content = _parse_content(d.pop("content", UNSET))
+
+        admin_test_result_metric_review_create_request = cls(
+            entity_id=entity_id,
+            entity_type=entity_type,
+            action=action,
+            test_result_metric_id=test_result_metric_id,
+            event=event,
+            content=content,
+        )
+
+        admin_test_result_metric_review_create_request.additional_properties = d
+        return admin_test_result_metric_review_create_request
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/admin_test_result_metric_review_edit_request.py b/src/maihem/api_client/maihem_client/models/admin_test_result_metric_review_edit_request.py
new file mode 100644
index 0000000..1cea6a5
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/admin_test_result_metric_review_edit_request.py
@@ -0,0 +1,136 @@
+from typing import Any, Dict, List, Type, TypeVar, Union, cast
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+from ..types import UNSET, Unset
+
+T = TypeVar("T", bound="AdminTestResultMetricReviewEditRequest")
+
+
+@_attrs_define
+class AdminTestResultMetricReviewEditRequest:
+    """
+    Attributes:
+        result (str):
+        entity_id (str):
+        entity_type (str):
+        test_result_metric_id (Union[None, Unset, str]):
+        score (Union[None, Unset, int]):
+        explanation (Union[None, Unset, str]):
+    """
+
+    result: str
+    entity_id: str
+    entity_type: str
+    test_result_metric_id: Union[None, Unset, str] = UNSET
+    score: Union[None, Unset, int] = UNSET
+    explanation: Union[None, Unset, str] = UNSET
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        result = self.result
+
+        entity_id = self.entity_id
+
+        entity_type = self.entity_type
+
+        test_result_metric_id: Union[None, Unset, str]
+        if isinstance(self.test_result_metric_id, Unset):
+            test_result_metric_id = UNSET
+        else:
+            test_result_metric_id = self.test_result_metric_id
+
+        score: Union[None, Unset, int]
+        if isinstance(self.score, Unset):
+            score = UNSET
+        else:
+            score = self.score
+
+        explanation: Union[None, Unset, str]
+        if isinstance(self.explanation, Unset):
+            explanation = UNSET
+        else:
+            explanation = self.explanation
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "result": result,
+                "entity_id": entity_id,
+                "entity_type": entity_type,
+            }
+        )
+        if test_result_metric_id is not UNSET:
+            field_dict["test_result_metric_id"] = test_result_metric_id
+        if score is not UNSET:
+            field_dict["score"] = score
+        if explanation is not UNSET:
+            field_dict["explanation"] = explanation
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        d = src_dict.copy()
+        result = d.pop("result")
+
+        entity_id = d.pop("entity_id")
+
+        entity_type = d.pop("entity_type")
+
+        def _parse_test_result_metric_id(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        test_result_metric_id = _parse_test_result_metric_id(d.pop("test_result_metric_id", UNSET))
+
+        def _parse_score(data: object) -> Union[None, Unset, int]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, int], data)
+
+        score = _parse_score(d.pop("score", UNSET))
+
+        def _parse_explanation(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        explanation = _parse_explanation(d.pop("explanation", UNSET))
+
+        admin_test_result_metric_review_edit_request = cls(
+            result=result,
+            entity_id=entity_id,
+            entity_type=entity_type,
+            test_result_metric_id=test_result_metric_id,
+            score=score,
+            explanation=explanation,
+        )
+
+        admin_test_result_metric_review_edit_request.additional_properties = d
+        return admin_test_result_metric_review_edit_request
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_create_request.py b/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_create_request.py
deleted file mode 100644
index fa4a344..0000000
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_create_request.py
+++ /dev/null
@@ -1,91 +0,0 @@
-from typing import Any, Dict, List, Type, TypeVar, Union, cast
-
-from attrs import define as _attrs_define
-from attrs import field as _attrs_field
-
-from ..models.api_schema_test_result_metric_feedback_create_request_feedback import (
-    APISchemaTestResultMetricFeedbackCreateRequestFeedback,
-)
-from ..types import UNSET, Unset
-
-T = TypeVar("T", bound="APISchemaTestResultMetricFeedbackCreateRequest")
-
-
-@_attrs_define
-class APISchemaTestResultMetricFeedbackCreateRequest:
-    """
-    Attributes:
-        feedback (Union[Unset, APISchemaTestResultMetricFeedbackCreateRequestFeedback]):  Default:
-            APISchemaTestResultMetricFeedbackCreateRequestFeedback.POSITIVE.
-        comments (Union[None, Unset, str]):
-    """
-
-    feedback: Union[Unset, APISchemaTestResultMetricFeedbackCreateRequestFeedback] = (
-        APISchemaTestResultMetricFeedbackCreateRequestFeedback.POSITIVE
-    )
-    comments: Union[None, Unset, str] = UNSET
-    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
-
-    def to_dict(self) -> Dict[str, Any]:
-        feedback: Union[Unset, str] = UNSET
-        if not isinstance(self.feedback, Unset):
-            feedback = self.feedback.value
-
-        comments: Union[None, Unset, str]
-        if isinstance(self.comments, Unset):
-            comments = UNSET
-        else:
-            comments = self.comments
-
-        field_dict: Dict[str, Any] = {}
-        field_dict.update(self.additional_properties)
-        field_dict.update({})
-        if feedback is not UNSET:
-            field_dict["feedback"] = feedback
-        if comments is not UNSET:
-            field_dict["comments"] = comments
-
-        return field_dict
-
-    @classmethod
-    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        d = src_dict.copy()
-        _feedback = d.pop("feedback", UNSET)
-        feedback: Union[Unset, APISchemaTestResultMetricFeedbackCreateRequestFeedback]
-        if isinstance(_feedback, Unset):
-            feedback = UNSET
-        else:
-            feedback = APISchemaTestResultMetricFeedbackCreateRequestFeedback(_feedback)
-
-        def _parse_comments(data: object) -> Union[None, Unset, str]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            return cast(Union[None, Unset, str], data)
-
-        comments = _parse_comments(d.pop("comments", UNSET))
-
-        api_schema_test_result_metric_feedback_create_request = cls(
-            feedback=feedback,
-            comments=comments,
-        )
-
-        api_schema_test_result_metric_feedback_create_request.additional_properties = d
-        return api_schema_test_result_metric_feedback_create_request
-
-    @property
-    def additional_keys(self) -> List[str]:
-        return list(self.additional_properties.keys())
-
-    def __getitem__(self, key: str) -> Any:
-        return self.additional_properties[key]
-
-    def __setitem__(self, key: str, value: Any) -> None:
-        self.additional_properties[key] = value
-
-    def __delitem__(self, key: str) -> None:
-        del self.additional_properties[key]
-
-    def __contains__(self, key: str) -> bool:
-        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations.py b/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations.py
deleted file mode 100644
index e265dad..0000000
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations.py
+++ /dev/null
@@ -1,380 +0,0 @@
-import datetime
-from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar, Union, cast
-
-from attrs import define as _attrs_define
-from attrs import field as _attrs_field
-from dateutil.parser import isoparse
-
-from ..models.test_result_enum import TestResultEnum
-from ..models.test_status_enum import TestStatusEnum
-from ..types import UNSET, Unset
-
-if TYPE_CHECKING:
-    from ..models.api_schema_links import APISchemaLinks
-    from ..models.api_schema_test_run_conversation_scores import APISchemaTestRunConversationScores
-    from ..models.api_schema_test_run_result_conversations_metric_scores_type_0 import (
-        APISchemaTestRunResultConversationsMetricScoresType0,
-    )
-    from ..models.api_schema_test_run_result_conversations_metric_summaries_type_0 import (
-        APISchemaTestRunResultConversationsMetricSummariesType0,
-    )
-    from ..models.conversation_nested import ConversationNested
-
-
-T = TypeVar("T", bound="APISchemaTestRunResultConversations")
-
-
-@_attrs_define
-class APISchemaTestRunResultConversations:
-    """
-    Attributes:
-        id (str):
-        created_at (datetime.datetime):
-        updated_at (datetime.datetime):
-        test_id (str):
-        status (TestStatusEnum):
-        started_at (Union[None, Unset, datetime.datetime]):
-        completed_at (Union[None, Unset, datetime.datetime]):
-        result (Union[None, TestResultEnum, Unset]):
-        result_score (Union[None, Unset, float]):
-        links (Union['APISchemaLinks', None, Unset]):
-        conversation_counts (Union['APISchemaTestRunConversationScores', None, Unset]):
-        metric_scores (Union['APISchemaTestRunResultConversationsMetricScoresType0', None, Unset]):
-        metric_summaries (Union['APISchemaTestRunResultConversationsMetricSummariesType0', None, Unset]):
-        conversations (Union[Unset, List['ConversationNested']]):
-    """
-
-    id: str
-    created_at: datetime.datetime
-    updated_at: datetime.datetime
-    test_id: str
-    status: TestStatusEnum
-    started_at: Union[None, Unset, datetime.datetime] = UNSET
-    completed_at: Union[None, Unset, datetime.datetime] = UNSET
-    result: Union[None, TestResultEnum, Unset] = UNSET
-    result_score: Union[None, Unset, float] = UNSET
-    links: Union["APISchemaLinks", None, Unset] = UNSET
-    conversation_counts: Union["APISchemaTestRunConversationScores", None, Unset] = UNSET
-    metric_scores: Union["APISchemaTestRunResultConversationsMetricScoresType0", None, Unset] = UNSET
-    metric_summaries: Union["APISchemaTestRunResultConversationsMetricSummariesType0", None, Unset] = UNSET
-    conversations: Union[Unset, List["ConversationNested"]] = UNSET
-    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
-
-    def to_dict(self) -> Dict[str, Any]:
-        from ..models.api_schema_links import APISchemaLinks
-        from ..models.api_schema_test_run_conversation_scores import APISchemaTestRunConversationScores
-        from ..models.api_schema_test_run_result_conversations_metric_scores_type_0 import (
-            APISchemaTestRunResultConversationsMetricScoresType0,
-        )
-        from ..models.api_schema_test_run_result_conversations_metric_summaries_type_0 import (
-            APISchemaTestRunResultConversationsMetricSummariesType0,
-        )
-
-        id = self.id
-
-        created_at = self.created_at.isoformat()
-
-        updated_at = self.updated_at.isoformat()
-
-        test_id = self.test_id
-
-        status = self.status.value
-
-        started_at: Union[None, Unset, str]
-        if isinstance(self.started_at, Unset):
-            started_at = UNSET
-        elif isinstance(self.started_at, datetime.datetime):
-            started_at = self.started_at.isoformat()
-        else:
-            started_at = self.started_at
-
-        completed_at: Union[None, Unset, str]
-        if isinstance(self.completed_at, Unset):
-            completed_at = UNSET
-        elif isinstance(self.completed_at, datetime.datetime):
-            completed_at = self.completed_at.isoformat()
-        else:
-            completed_at = self.completed_at
-
-        result: Union[None, Unset, str]
-        if isinstance(self.result, Unset):
-            result = UNSET
-        elif isinstance(self.result, TestResultEnum):
-            result = self.result.value
-        else:
-            result = self.result
-
-        result_score: Union[None, Unset, float]
-        if isinstance(self.result_score, Unset):
-            result_score = UNSET
-        else:
-            result_score = self.result_score
-
-        links: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.links, Unset):
-            links = UNSET
-        elif isinstance(self.links, APISchemaLinks):
-            links = self.links.to_dict()
-        else:
-            links = self.links
-
-        conversation_counts: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.conversation_counts, Unset):
-            conversation_counts = UNSET
-        elif isinstance(self.conversation_counts, APISchemaTestRunConversationScores):
-            conversation_counts = self.conversation_counts.to_dict()
-        else:
-            conversation_counts = self.conversation_counts
-
-        metric_scores: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.metric_scores, Unset):
-            metric_scores = UNSET
-        elif isinstance(self.metric_scores, APISchemaTestRunResultConversationsMetricScoresType0):
-            metric_scores = self.metric_scores.to_dict()
-        else:
-            metric_scores = self.metric_scores
-
-        metric_summaries: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.metric_summaries, Unset):
-            metric_summaries = UNSET
-        elif isinstance(self.metric_summaries, APISchemaTestRunResultConversationsMetricSummariesType0):
-            metric_summaries = self.metric_summaries.to_dict()
-        else:
-            metric_summaries = self.metric_summaries
-
-        conversations: Union[Unset, List[Dict[str, Any]]] = UNSET
-        if not isinstance(self.conversations, Unset):
-            conversations = []
-            for conversations_item_data in self.conversations:
-                conversations_item = conversations_item_data.to_dict()
-                conversations.append(conversations_item)
-
-        field_dict: Dict[str, Any] = {}
-        field_dict.update(self.additional_properties)
-        field_dict.update(
-            {
-                "id": id,
-                "created_at": created_at,
-                "updated_at": updated_at,
-                "test_id": test_id,
-                "status": status,
-            }
-        )
-        if started_at is not UNSET:
-            field_dict["started_at"] = started_at
-        if completed_at is not UNSET:
-            field_dict["completed_at"] = completed_at
-        if result is not UNSET:
-            field_dict["result"] = result
-        if result_score is not UNSET:
-            field_dict["result_score"] = result_score
-        if links is not UNSET:
-            field_dict["links"] = links
-        if conversation_counts is not UNSET:
-            field_dict["conversation_counts"] = conversation_counts
-        if metric_scores is not UNSET:
-            field_dict["metric_scores"] = metric_scores
-        if metric_summaries is not UNSET:
-            field_dict["metric_summaries"] = metric_summaries
-        if conversations is not UNSET:
-            field_dict["conversations"] = conversations
-
-        return field_dict
-
-    @classmethod
-    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_links import APISchemaLinks
-        from ..models.api_schema_test_run_conversation_scores import APISchemaTestRunConversationScores
-        from ..models.api_schema_test_run_result_conversations_metric_scores_type_0 import (
-            APISchemaTestRunResultConversationsMetricScoresType0,
-        )
-        from ..models.api_schema_test_run_result_conversations_metric_summaries_type_0 import (
-            APISchemaTestRunResultConversationsMetricSummariesType0,
-        )
-        from ..models.conversation_nested import ConversationNested
-
-        d = src_dict.copy()
-        id = d.pop("id")
-
-        created_at = isoparse(d.pop("created_at"))
-
-        updated_at = isoparse(d.pop("updated_at"))
-
-        test_id = d.pop("test_id")
-
-        status = TestStatusEnum(d.pop("status"))
-
-        def _parse_started_at(data: object) -> Union[None, Unset, datetime.datetime]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, str):
-                    raise TypeError()
-                started_at_type_0 = isoparse(data)
-
-                return started_at_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union[None, Unset, datetime.datetime], data)
-
-        started_at = _parse_started_at(d.pop("started_at", UNSET))
-
-        def _parse_completed_at(data: object) -> Union[None, Unset, datetime.datetime]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, str):
-                    raise TypeError()
-                completed_at_type_0 = isoparse(data)
-
-                return completed_at_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union[None, Unset, datetime.datetime], data)
-
-        completed_at = _parse_completed_at(d.pop("completed_at", UNSET))
-
-        def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, str):
-                    raise TypeError()
-                result_type_0 = TestResultEnum(data)
-
-                return result_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union[None, TestResultEnum, Unset], data)
-
-        result = _parse_result(d.pop("result", UNSET))
-
-        def _parse_result_score(data: object) -> Union[None, Unset, float]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            return cast(Union[None, Unset, float], data)
-
-        result_score = _parse_result_score(d.pop("result_score", UNSET))
-
-        def _parse_links(data: object) -> Union["APISchemaLinks", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                links_type_0 = APISchemaLinks.from_dict(data)
-
-                return links_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaLinks", None, Unset], data)
-
-        links = _parse_links(d.pop("links", UNSET))
-
-        def _parse_conversation_counts(data: object) -> Union["APISchemaTestRunConversationScores", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                conversation_counts_type_0 = APISchemaTestRunConversationScores.from_dict(data)
-
-                return conversation_counts_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaTestRunConversationScores", None, Unset], data)
-
-        conversation_counts = _parse_conversation_counts(d.pop("conversation_counts", UNSET))
-
-        def _parse_metric_scores(
-            data: object,
-        ) -> Union["APISchemaTestRunResultConversationsMetricScoresType0", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                metric_scores_type_0 = APISchemaTestRunResultConversationsMetricScoresType0.from_dict(data)
-
-                return metric_scores_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaTestRunResultConversationsMetricScoresType0", None, Unset], data)
-
-        metric_scores = _parse_metric_scores(d.pop("metric_scores", UNSET))
-
-        def _parse_metric_summaries(
-            data: object,
-        ) -> Union["APISchemaTestRunResultConversationsMetricSummariesType0", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                metric_summaries_type_0 = APISchemaTestRunResultConversationsMetricSummariesType0.from_dict(data)
-
-                return metric_summaries_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaTestRunResultConversationsMetricSummariesType0", None, Unset], data)
-
-        metric_summaries = _parse_metric_summaries(d.pop("metric_summaries", UNSET))
-
-        conversations = []
-        _conversations = d.pop("conversations", UNSET)
-        for conversations_item_data in _conversations or []:
-            conversations_item = ConversationNested.from_dict(conversations_item_data)
-
-            conversations.append(conversations_item)
-
-        api_schema_test_run_result_conversations = cls(
-            id=id,
-            created_at=created_at,
-            updated_at=updated_at,
-            test_id=test_id,
-            status=status,
-            started_at=started_at,
-            completed_at=completed_at,
-            result=result,
-            result_score=result_score,
-            links=links,
-            conversation_counts=conversation_counts,
-            metric_scores=metric_scores,
-            metric_summaries=metric_summaries,
-            conversations=conversations,
-        )
-
-        api_schema_test_run_result_conversations.additional_properties = d
-        return api_schema_test_run_result_conversations
-
-    @property
-    def additional_keys(self) -> List[str]:
-        return list(self.additional_properties.keys())
-
-    def __getitem__(self, key: str) -> Any:
-        return self.additional_properties[key]
-
-    def __setitem__(self, key: str, value: Any) -> None:
-        self.additional_properties[key] = value
-
-    def __delitem__(self, key: str) -> None:
-        del self.additional_properties[key]
-
-    def __contains__(self, key: str) -> bool:
-        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics.py b/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics.py
deleted file mode 100644
index a2af795..0000000
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics.py
+++ /dev/null
@@ -1,357 +0,0 @@
-import datetime
-from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar, Union, cast
-
-from attrs import define as _attrs_define
-from attrs import field as _attrs_field
-from dateutil.parser import isoparse
-
-from ..models.test_result_enum import TestResultEnum
-from ..models.test_status_enum import TestStatusEnum
-from ..types import UNSET, Unset
-
-if TYPE_CHECKING:
-    from ..models.api_schema_links import APISchemaLinks
-    from ..models.api_schema_test_run_conversation_scores import APISchemaTestRunConversationScores
-    from ..models.api_schema_test_run_result_metrics_metric_scores_type_0 import (
-        APISchemaTestRunResultMetricsMetricScoresType0,
-    )
-    from ..models.api_schema_test_run_result_metrics_metric_summaries_type_0 import (
-        APISchemaTestRunResultMetricsMetricSummariesType0,
-    )
-
-
-T = TypeVar("T", bound="APISchemaTestRunResultMetrics")
-
-
-@_attrs_define
-class APISchemaTestRunResultMetrics:
-    """
-    Attributes:
-        id (str):
-        created_at (datetime.datetime):
-        updated_at (datetime.datetime):
-        test_id (str):
-        status (TestStatusEnum):
-        started_at (Union[None, Unset, datetime.datetime]):
-        completed_at (Union[None, Unset, datetime.datetime]):
-        result (Union[None, TestResultEnum, Unset]):
-        result_score (Union[None, Unset, float]):
-        links (Union['APISchemaLinks', None, Unset]):
-        conversation_counts (Union['APISchemaTestRunConversationScores', None, Unset]):
-        metric_scores (Union['APISchemaTestRunResultMetricsMetricScoresType0', None, Unset]):
-        metric_summaries (Union['APISchemaTestRunResultMetricsMetricSummariesType0', None, Unset]):
-    """
-
-    id: str
-    created_at: datetime.datetime
-    updated_at: datetime.datetime
-    test_id: str
-    status: TestStatusEnum
-    started_at: Union[None, Unset, datetime.datetime] = UNSET
-    completed_at: Union[None, Unset, datetime.datetime] = UNSET
-    result: Union[None, TestResultEnum, Unset] = UNSET
-    result_score: Union[None, Unset, float] = UNSET
-    links: Union["APISchemaLinks", None, Unset] = UNSET
-    conversation_counts: Union["APISchemaTestRunConversationScores", None, Unset] = UNSET
-    metric_scores: Union["APISchemaTestRunResultMetricsMetricScoresType0", None, Unset] = UNSET
-    metric_summaries: Union["APISchemaTestRunResultMetricsMetricSummariesType0", None, Unset] = UNSET
-    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
-
-    def to_dict(self) -> Dict[str, Any]:
-        from ..models.api_schema_links import APISchemaLinks
-        from ..models.api_schema_test_run_conversation_scores import APISchemaTestRunConversationScores
-        from ..models.api_schema_test_run_result_metrics_metric_scores_type_0 import (
-            APISchemaTestRunResultMetricsMetricScoresType0,
-        )
-        from ..models.api_schema_test_run_result_metrics_metric_summaries_type_0 import (
-            APISchemaTestRunResultMetricsMetricSummariesType0,
-        )
-
-        id = self.id
-
-        created_at = self.created_at.isoformat()
-
-        updated_at = self.updated_at.isoformat()
-
-        test_id = self.test_id
-
-        status = self.status.value
-
-        started_at: Union[None, Unset, str]
-        if isinstance(self.started_at, Unset):
-            started_at = UNSET
-        elif isinstance(self.started_at, datetime.datetime):
-            started_at = self.started_at.isoformat()
-        else:
-            started_at = self.started_at
-
-        completed_at: Union[None, Unset, str]
-        if isinstance(self.completed_at, Unset):
-            completed_at = UNSET
-        elif isinstance(self.completed_at, datetime.datetime):
-            completed_at = self.completed_at.isoformat()
-        else:
-            completed_at = self.completed_at
-
-        result: Union[None, Unset, str]
-        if isinstance(self.result, Unset):
-            result = UNSET
-        elif isinstance(self.result, TestResultEnum):
-            result = self.result.value
-        else:
-            result = self.result
-
-        result_score: Union[None, Unset, float]
-        if isinstance(self.result_score, Unset):
-            result_score = UNSET
-        else:
-            result_score = self.result_score
-
-        links: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.links, Unset):
-            links = UNSET
-        elif isinstance(self.links, APISchemaLinks):
-            links = self.links.to_dict()
-        else:
-            links = self.links
-
-        conversation_counts: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.conversation_counts, Unset):
-            conversation_counts = UNSET
-        elif isinstance(self.conversation_counts, APISchemaTestRunConversationScores):
-            conversation_counts = self.conversation_counts.to_dict()
-        else:
-            conversation_counts = self.conversation_counts
-
-        metric_scores: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.metric_scores, Unset):
-            metric_scores = UNSET
-        elif isinstance(self.metric_scores, APISchemaTestRunResultMetricsMetricScoresType0):
-            metric_scores = self.metric_scores.to_dict()
-        else:
-            metric_scores = self.metric_scores
-
-        metric_summaries: Union[Dict[str, Any], None, Unset]
-        if isinstance(self.metric_summaries, Unset):
-            metric_summaries = UNSET
-        elif isinstance(self.metric_summaries, APISchemaTestRunResultMetricsMetricSummariesType0):
-            metric_summaries = self.metric_summaries.to_dict()
-        else:
-            metric_summaries = self.metric_summaries
-
-        field_dict: Dict[str, Any] = {}
-        field_dict.update(self.additional_properties)
-        field_dict.update(
-            {
-                "id": id,
-                "created_at": created_at,
-                "updated_at": updated_at,
-                "test_id": test_id,
-                "status": status,
-            }
-        )
-        if started_at is not UNSET:
-            field_dict["started_at"] = started_at
-        if completed_at is not UNSET:
-            field_dict["completed_at"] = completed_at
-        if result is not UNSET:
-            field_dict["result"] = result
-        if result_score is not UNSET:
-            field_dict["result_score"] = result_score
-        if links is not UNSET:
-            field_dict["links"] = links
-        if conversation_counts is not UNSET:
-            field_dict["conversation_counts"] = conversation_counts
-        if metric_scores is not UNSET:
-            field_dict["metric_scores"] = metric_scores
-        if metric_summaries is not UNSET:
-            field_dict["metric_summaries"] = metric_summaries
-
-        return field_dict
-
-    @classmethod
-    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_links import APISchemaLinks
-        from ..models.api_schema_test_run_conversation_scores import APISchemaTestRunConversationScores
-        from ..models.api_schema_test_run_result_metrics_metric_scores_type_0 import (
-            APISchemaTestRunResultMetricsMetricScoresType0,
-        )
-        from ..models.api_schema_test_run_result_metrics_metric_summaries_type_0 import (
-            APISchemaTestRunResultMetricsMetricSummariesType0,
-        )
-
-        d = src_dict.copy()
-        id = d.pop("id")
-
-        created_at = isoparse(d.pop("created_at"))
-
-        updated_at = isoparse(d.pop("updated_at"))
-
-        test_id = d.pop("test_id")
-
-        status = TestStatusEnum(d.pop("status"))
-
-        def _parse_started_at(data: object) -> Union[None, Unset, datetime.datetime]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, str):
-                    raise TypeError()
-                started_at_type_0 = isoparse(data)
-
-                return started_at_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union[None, Unset, datetime.datetime], data)
-
-        started_at = _parse_started_at(d.pop("started_at", UNSET))
-
-        def _parse_completed_at(data: object) -> Union[None, Unset, datetime.datetime]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, str):
-                    raise TypeError()
-                completed_at_type_0 = isoparse(data)
-
-                return completed_at_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union[None, Unset, datetime.datetime], data)
-
-        completed_at = _parse_completed_at(d.pop("completed_at", UNSET))
-
-        def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, str):
-                    raise TypeError()
-                result_type_0 = TestResultEnum(data)
-
-                return result_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union[None, TestResultEnum, Unset], data)
-
-        result = _parse_result(d.pop("result", UNSET))
-
-        def _parse_result_score(data: object) -> Union[None, Unset, float]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            return cast(Union[None, Unset, float], data)
-
-        result_score = _parse_result_score(d.pop("result_score", UNSET))
-
-        def _parse_links(data: object) -> Union["APISchemaLinks", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                links_type_0 = APISchemaLinks.from_dict(data)
-
-                return links_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaLinks", None, Unset], data)
-
-        links = _parse_links(d.pop("links", UNSET))
-
-        def _parse_conversation_counts(data: object) -> Union["APISchemaTestRunConversationScores", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                conversation_counts_type_0 = APISchemaTestRunConversationScores.from_dict(data)
-
-                return conversation_counts_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaTestRunConversationScores", None, Unset], data)
-
-        conversation_counts = _parse_conversation_counts(d.pop("conversation_counts", UNSET))
-
-        def _parse_metric_scores(data: object) -> Union["APISchemaTestRunResultMetricsMetricScoresType0", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                metric_scores_type_0 = APISchemaTestRunResultMetricsMetricScoresType0.from_dict(data)
-
-                return metric_scores_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaTestRunResultMetricsMetricScoresType0", None, Unset], data)
-
-        metric_scores = _parse_metric_scores(d.pop("metric_scores", UNSET))
-
-        def _parse_metric_summaries(
-            data: object,
-        ) -> Union["APISchemaTestRunResultMetricsMetricSummariesType0", None, Unset]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            try:
-                if not isinstance(data, dict):
-                    raise TypeError()
-                metric_summaries_type_0 = APISchemaTestRunResultMetricsMetricSummariesType0.from_dict(data)
-
-                return metric_summaries_type_0
-            except:  # noqa: E722
-                pass
-            return cast(Union["APISchemaTestRunResultMetricsMetricSummariesType0", None, Unset], data)
-
-        metric_summaries = _parse_metric_summaries(d.pop("metric_summaries", UNSET))
-
-        api_schema_test_run_result_metrics = cls(
-            id=id,
-            created_at=created_at,
-            updated_at=updated_at,
-            test_id=test_id,
-            status=status,
-            started_at=started_at,
-            completed_at=completed_at,
-            result=result,
-            result_score=result_score,
-            links=links,
-            conversation_counts=conversation_counts,
-            metric_scores=metric_scores,
-            metric_summaries=metric_summaries,
-        )
-
-        api_schema_test_run_result_metrics.additional_properties = d
-        return api_schema_test_run_result_metrics
-
-    @property
-    def additional_keys(self) -> List[str]:
-        return list(self.additional_properties.keys())
-
-    def __getitem__(self, key: str) -> Any:
-        return self.additional_properties[key]
-
-    def __setitem__(self, key: str, value: Any) -> None:
-        self.additional_properties[key] = value
-
-    def __delitem__(self, key: str) -> None:
-        del self.additional_properties[key]
-
-    def __contains__(self, key: str) -> bool:
-        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/org_base.py b/src/maihem/api_client/maihem_client/models/create_test_run_request.py
similarity index 69%
rename from src/maihem/api_client/maihem_client/models/org_base.py
rename to src/maihem/api_client/maihem_client/models/create_test_run_request.py
index a4a5d49..a99bb7e 100644
--- a/src/maihem/api_client/maihem_client/models/org_base.py
+++ b/src/maihem/api_client/maihem_client/models/create_test_run_request.py
@@ -5,29 +5,29 @@
 
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="OrgBase")
+T = TypeVar("T", bound="CreateTestRunRequest")
 
 
 @_attrs_define
-class OrgBase:
+class CreateTestRunRequest:
     """
     Attributes:
         name (str):
-        idp_org_id (Union[None, Unset, str]):
+        label (Union[None, Unset, str]):
     """
 
     name: str
-    idp_org_id: Union[None, Unset, str] = UNSET
+    label: Union[None, Unset, str] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
         name = self.name
 
-        idp_org_id: Union[None, Unset, str]
-        if isinstance(self.idp_org_id, Unset):
-            idp_org_id = UNSET
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
         else:
-            idp_org_id = self.idp_org_id
+            label = self.label
 
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
@@ -36,8 +36,8 @@ def to_dict(self) -> Dict[str, Any]:
                 "name": name,
             }
         )
-        if idp_org_id is not UNSET:
-            field_dict["idp_org_id"] = idp_org_id
+        if label is not UNSET:
+            field_dict["label"] = label
 
         return field_dict
 
@@ -46,22 +46,22 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
         name = d.pop("name")
 
-        def _parse_idp_org_id(data: object) -> Union[None, Unset, str]:
+        def _parse_label(data: object) -> Union[None, Unset, str]:
             if data is None:
                 return data
             if isinstance(data, Unset):
                 return data
             return cast(Union[None, Unset, str], data)
 
-        idp_org_id = _parse_idp_org_id(d.pop("idp_org_id", UNSET))
+        label = _parse_label(d.pop("label", UNSET))
 
-        org_base = cls(
+        create_test_run_request = cls(
             name=name,
-            idp_org_id=idp_org_id,
+            label=label,
         )
 
-        org_base.additional_properties = d
-        return org_base
+        create_test_run_request.additional_properties = d
+        return create_test_run_request
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test.py b/src/maihem/api_client/maihem_client/models/test.py
similarity index 54%
rename from src/maihem/api_client/maihem_client/models/api_schema_test.py
rename to src/maihem/api_client/maihem_client/models/test.py
index 834b013..95dd6a0 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test.py
+++ b/src/maihem/api_client/maihem_client/models/test.py
@@ -5,36 +5,41 @@
 from attrs import field as _attrs_field
 from dateutil.parser import isoparse
 
-from ..models.agent_maihem_role import AgentMaihemRole
 from ..models.agent_type import AgentType
 from ..models.test_result_enum import TestResultEnum
 from ..models.test_status_enum import TestStatusEnum
 from ..types import UNSET, Unset
 
 if TYPE_CHECKING:
-    from ..models.api_schema_test_metrics_config import APISchemaTestMetricsConfig
+    from ..models.test_documents_type_0 import TestDocumentsType0
+    from ..models.test_metrics_config import TestMetricsConfig
 
 
-T = TypeVar("T", bound="APISchemaTest")
+T = TypeVar("T", bound="Test")
 
 
 @_attrs_define
-class APISchemaTest:
+class Test:
     """
     Attributes:
         id (str):
         created_at (datetime.datetime):
         updated_at (datetime.datetime):
-        identifier (str):
+        name (str):
         initiating_agent (AgentType):
         agent_target_id (str):
-        metrics_config (APISchemaTestMetricsConfig):
-        name (Union[None, Unset, str]):
+        agent_target_name (str):
+        metrics_config (TestMetricsConfig):
+        label (Union[None, Unset, str]):
+        agent_target_label (Union[None, Unset, str]):
         conversation_turns_max (Union[None, Unset, int]):
         agent_maihem_behavior_prompt (Union[None, Unset, str]):
-        agent_maihem_roles (Union[Unset, List[AgentMaihemRole]]):
+        agent_maihem_goal_prompt (Union[None, Unset, str]):
+        agent_maihem_population_prompt (Union[None, Unset, str]):
+        documents (Union['TestDocumentsType0', None, Unset]):
         last_test_run_id (Union[None, Unset, str]):
-        last_test_run_at (Union[None, Unset, datetime.datetime]):
+        last_test_run_started_at (Union[None, Unset, datetime.datetime]):
+        last_test_run_completed_at (Union[None, Unset, datetime.datetime]):
         last_test_run_status (Union[None, TestStatusEnum, Unset]):
         last_test_run_result (Union[None, TestResultEnum, Unset]):
         last_test_run_result_score (Union[None, Unset, float]):
@@ -43,41 +48,56 @@ class APISchemaTest:
     id: str
     created_at: datetime.datetime
     updated_at: datetime.datetime
-    identifier: str
+    name: str
     initiating_agent: AgentType
     agent_target_id: str
-    metrics_config: "APISchemaTestMetricsConfig"
-    name: Union[None, Unset, str] = UNSET
+    agent_target_name: str
+    metrics_config: "TestMetricsConfig"
+    label: Union[None, Unset, str] = UNSET
+    agent_target_label: Union[None, Unset, str] = UNSET
     conversation_turns_max: Union[None, Unset, int] = UNSET
     agent_maihem_behavior_prompt: Union[None, Unset, str] = UNSET
-    agent_maihem_roles: Union[Unset, List[AgentMaihemRole]] = UNSET
+    agent_maihem_goal_prompt: Union[None, Unset, str] = UNSET
+    agent_maihem_population_prompt: Union[None, Unset, str] = UNSET
+    documents: Union["TestDocumentsType0", None, Unset] = UNSET
     last_test_run_id: Union[None, Unset, str] = UNSET
-    last_test_run_at: Union[None, Unset, datetime.datetime] = UNSET
+    last_test_run_started_at: Union[None, Unset, datetime.datetime] = UNSET
+    last_test_run_completed_at: Union[None, Unset, datetime.datetime] = UNSET
     last_test_run_status: Union[None, TestStatusEnum, Unset] = UNSET
     last_test_run_result: Union[None, TestResultEnum, Unset] = UNSET
     last_test_run_result_score: Union[None, Unset, float] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
+        from ..models.test_documents_type_0 import TestDocumentsType0
+
         id = self.id
 
         created_at = self.created_at.isoformat()
 
         updated_at = self.updated_at.isoformat()
 
-        identifier = self.identifier
+        name = self.name
 
         initiating_agent = self.initiating_agent.value
 
         agent_target_id = self.agent_target_id
 
+        agent_target_name = self.agent_target_name
+
         metrics_config = self.metrics_config.to_dict()
 
-        name: Union[None, Unset, str]
-        if isinstance(self.name, Unset):
-            name = UNSET
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
+        else:
+            label = self.label
+
+        agent_target_label: Union[None, Unset, str]
+        if isinstance(self.agent_target_label, Unset):
+            agent_target_label = UNSET
         else:
-            name = self.name
+            agent_target_label = self.agent_target_label
 
         conversation_turns_max: Union[None, Unset, int]
         if isinstance(self.conversation_turns_max, Unset):
@@ -91,12 +111,25 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             agent_maihem_behavior_prompt = self.agent_maihem_behavior_prompt
 
-        agent_maihem_roles: Union[Unset, List[str]] = UNSET
-        if not isinstance(self.agent_maihem_roles, Unset):
-            agent_maihem_roles = []
-            for agent_maihem_roles_item_data in self.agent_maihem_roles:
-                agent_maihem_roles_item = agent_maihem_roles_item_data.value
-                agent_maihem_roles.append(agent_maihem_roles_item)
+        agent_maihem_goal_prompt: Union[None, Unset, str]
+        if isinstance(self.agent_maihem_goal_prompt, Unset):
+            agent_maihem_goal_prompt = UNSET
+        else:
+            agent_maihem_goal_prompt = self.agent_maihem_goal_prompt
+
+        agent_maihem_population_prompt: Union[None, Unset, str]
+        if isinstance(self.agent_maihem_population_prompt, Unset):
+            agent_maihem_population_prompt = UNSET
+        else:
+            agent_maihem_population_prompt = self.agent_maihem_population_prompt
+
+        documents: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.documents, Unset):
+            documents = UNSET
+        elif isinstance(self.documents, TestDocumentsType0):
+            documents = self.documents.to_dict()
+        else:
+            documents = self.documents
 
         last_test_run_id: Union[None, Unset, str]
         if isinstance(self.last_test_run_id, Unset):
@@ -104,13 +137,21 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             last_test_run_id = self.last_test_run_id
 
-        last_test_run_at: Union[None, Unset, str]
-        if isinstance(self.last_test_run_at, Unset):
-            last_test_run_at = UNSET
-        elif isinstance(self.last_test_run_at, datetime.datetime):
-            last_test_run_at = self.last_test_run_at.isoformat()
+        last_test_run_started_at: Union[None, Unset, str]
+        if isinstance(self.last_test_run_started_at, Unset):
+            last_test_run_started_at = UNSET
+        elif isinstance(self.last_test_run_started_at, datetime.datetime):
+            last_test_run_started_at = self.last_test_run_started_at.isoformat()
+        else:
+            last_test_run_started_at = self.last_test_run_started_at
+
+        last_test_run_completed_at: Union[None, Unset, str]
+        if isinstance(self.last_test_run_completed_at, Unset):
+            last_test_run_completed_at = UNSET
+        elif isinstance(self.last_test_run_completed_at, datetime.datetime):
+            last_test_run_completed_at = self.last_test_run_completed_at.isoformat()
         else:
-            last_test_run_at = self.last_test_run_at
+            last_test_run_completed_at = self.last_test_run_completed_at
 
         last_test_run_status: Union[None, Unset, str]
         if isinstance(self.last_test_run_status, Unset):
@@ -141,24 +182,33 @@ def to_dict(self) -> Dict[str, Any]:
                 "id": id,
                 "created_at": created_at,
                 "updated_at": updated_at,
-                "identifier": identifier,
+                "name": name,
                 "initiating_agent": initiating_agent,
                 "agent_target_id": agent_target_id,
+                "agent_target_name": agent_target_name,
                 "metrics_config": metrics_config,
             }
         )
-        if name is not UNSET:
-            field_dict["name"] = name
+        if label is not UNSET:
+            field_dict["label"] = label
+        if agent_target_label is not UNSET:
+            field_dict["agent_target_label"] = agent_target_label
         if conversation_turns_max is not UNSET:
             field_dict["conversation_turns_max"] = conversation_turns_max
         if agent_maihem_behavior_prompt is not UNSET:
             field_dict["agent_maihem_behavior_prompt"] = agent_maihem_behavior_prompt
-        if agent_maihem_roles is not UNSET:
-            field_dict["agent_maihem_roles"] = agent_maihem_roles
+        if agent_maihem_goal_prompt is not UNSET:
+            field_dict["agent_maihem_goal_prompt"] = agent_maihem_goal_prompt
+        if agent_maihem_population_prompt is not UNSET:
+            field_dict["agent_maihem_population_prompt"] = agent_maihem_population_prompt
+        if documents is not UNSET:
+            field_dict["documents"] = documents
         if last_test_run_id is not UNSET:
             field_dict["last_test_run_id"] = last_test_run_id
-        if last_test_run_at is not UNSET:
-            field_dict["last_test_run_at"] = last_test_run_at
+        if last_test_run_started_at is not UNSET:
+            field_dict["last_test_run_started_at"] = last_test_run_started_at
+        if last_test_run_completed_at is not UNSET:
+            field_dict["last_test_run_completed_at"] = last_test_run_completed_at
         if last_test_run_status is not UNSET:
             field_dict["last_test_run_status"] = last_test_run_status
         if last_test_run_result is not UNSET:
@@ -170,7 +220,8 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_test_metrics_config import APISchemaTestMetricsConfig
+        from ..models.test_documents_type_0 import TestDocumentsType0
+        from ..models.test_metrics_config import TestMetricsConfig
 
         d = src_dict.copy()
         id = d.pop("id")
@@ -179,22 +230,33 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         updated_at = isoparse(d.pop("updated_at"))
 
-        identifier = d.pop("identifier")
+        name = d.pop("name")
 
         initiating_agent = AgentType(d.pop("initiating_agent"))
 
         agent_target_id = d.pop("agent_target_id")
 
-        metrics_config = APISchemaTestMetricsConfig.from_dict(d.pop("metrics_config"))
+        agent_target_name = d.pop("agent_target_name")
+
+        metrics_config = TestMetricsConfig.from_dict(d.pop("metrics_config"))
 
-        def _parse_name(data: object) -> Union[None, Unset, str]:
+        def _parse_label(data: object) -> Union[None, Unset, str]:
             if data is None:
                 return data
             if isinstance(data, Unset):
                 return data
             return cast(Union[None, Unset, str], data)
 
-        name = _parse_name(d.pop("name", UNSET))
+        label = _parse_label(d.pop("label", UNSET))
+
+        def _parse_agent_target_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_target_label = _parse_agent_target_label(d.pop("agent_target_label", UNSET))
 
         def _parse_conversation_turns_max(data: object) -> Union[None, Unset, int]:
             if data is None:
@@ -214,12 +276,42 @@ def _parse_agent_maihem_behavior_prompt(data: object) -> Union[None, Unset, str]
 
         agent_maihem_behavior_prompt = _parse_agent_maihem_behavior_prompt(d.pop("agent_maihem_behavior_prompt", UNSET))
 
-        agent_maihem_roles = []
-        _agent_maihem_roles = d.pop("agent_maihem_roles", UNSET)
-        for agent_maihem_roles_item_data in _agent_maihem_roles or []:
-            agent_maihem_roles_item = AgentMaihemRole(agent_maihem_roles_item_data)
+        def _parse_agent_maihem_goal_prompt(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_maihem_goal_prompt = _parse_agent_maihem_goal_prompt(d.pop("agent_maihem_goal_prompt", UNSET))
+
+        def _parse_agent_maihem_population_prompt(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_maihem_population_prompt = _parse_agent_maihem_population_prompt(
+            d.pop("agent_maihem_population_prompt", UNSET)
+        )
 
-            agent_maihem_roles.append(agent_maihem_roles_item)
+        def _parse_documents(data: object) -> Union["TestDocumentsType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                documents_type_0 = TestDocumentsType0.from_dict(data)
+
+                return documents_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestDocumentsType0", None, Unset], data)
+
+        documents = _parse_documents(d.pop("documents", UNSET))
 
         def _parse_last_test_run_id(data: object) -> Union[None, Unset, str]:
             if data is None:
@@ -230,7 +322,7 @@ def _parse_last_test_run_id(data: object) -> Union[None, Unset, str]:
 
         last_test_run_id = _parse_last_test_run_id(d.pop("last_test_run_id", UNSET))
 
-        def _parse_last_test_run_at(data: object) -> Union[None, Unset, datetime.datetime]:
+        def _parse_last_test_run_started_at(data: object) -> Union[None, Unset, datetime.datetime]:
             if data is None:
                 return data
             if isinstance(data, Unset):
@@ -238,14 +330,31 @@ def _parse_last_test_run_at(data: object) -> Union[None, Unset, datetime.datetim
             try:
                 if not isinstance(data, str):
                     raise TypeError()
-                last_test_run_at_type_0 = isoparse(data)
+                last_test_run_started_at_type_0 = isoparse(data)
 
-                return last_test_run_at_type_0
+                return last_test_run_started_at_type_0
             except:  # noqa: E722
                 pass
             return cast(Union[None, Unset, datetime.datetime], data)
 
-        last_test_run_at = _parse_last_test_run_at(d.pop("last_test_run_at", UNSET))
+        last_test_run_started_at = _parse_last_test_run_started_at(d.pop("last_test_run_started_at", UNSET))
+
+        def _parse_last_test_run_completed_at(data: object) -> Union[None, Unset, datetime.datetime]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, str):
+                    raise TypeError()
+                last_test_run_completed_at_type_0 = isoparse(data)
+
+                return last_test_run_completed_at_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union[None, Unset, datetime.datetime], data)
+
+        last_test_run_completed_at = _parse_last_test_run_completed_at(d.pop("last_test_run_completed_at", UNSET))
 
         def _parse_last_test_run_status(data: object) -> Union[None, TestStatusEnum, Unset]:
             if data is None:
@@ -290,27 +399,32 @@ def _parse_last_test_run_result_score(data: object) -> Union[None, Unset, float]
 
         last_test_run_result_score = _parse_last_test_run_result_score(d.pop("last_test_run_result_score", UNSET))
 
-        api_schema_test = cls(
+        test = cls(
             id=id,
             created_at=created_at,
             updated_at=updated_at,
-            identifier=identifier,
+            name=name,
             initiating_agent=initiating_agent,
             agent_target_id=agent_target_id,
+            agent_target_name=agent_target_name,
             metrics_config=metrics_config,
-            name=name,
+            label=label,
+            agent_target_label=agent_target_label,
             conversation_turns_max=conversation_turns_max,
             agent_maihem_behavior_prompt=agent_maihem_behavior_prompt,
-            agent_maihem_roles=agent_maihem_roles,
+            agent_maihem_goal_prompt=agent_maihem_goal_prompt,
+            agent_maihem_population_prompt=agent_maihem_population_prompt,
+            documents=documents,
             last_test_run_id=last_test_run_id,
-            last_test_run_at=last_test_run_at,
+            last_test_run_started_at=last_test_run_started_at,
+            last_test_run_completed_at=last_test_run_completed_at,
             last_test_run_status=last_test_run_status,
             last_test_run_result=last_test_run_result,
             last_test_run_result_score=last_test_run_result_score,
         )
 
-        api_schema_test.additional_properties = d
-        return api_schema_test
+        test.additional_properties = d
+        return test
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_create_request.py b/src/maihem/api_client/maihem_client/models/test_create_request.py
similarity index 53%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_create_request.py
rename to src/maihem/api_client/maihem_client/models/test_create_request.py
index 4c7067b..9655c9c 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_create_request.py
+++ b/src/maihem/api_client/maihem_client/models/test_create_request.py
@@ -7,48 +7,57 @@
 from ..types import UNSET, Unset
 
 if TYPE_CHECKING:
-    from ..models.api_schema_test_create_request_metrics_config import APISchemaTestCreateRequestMetricsConfig
+    from ..models.test_create_request_documents_type_0 import TestCreateRequestDocumentsType0
+    from ..models.test_create_request_metrics_config import TestCreateRequestMetricsConfig
 
 
-T = TypeVar("T", bound="APISchemaTestCreateRequest")
+T = TypeVar("T", bound="TestCreateRequest")
 
 
 @_attrs_define
-class APISchemaTestCreateRequest:
+class TestCreateRequest:
     """
     Attributes:
-        identifier (str):
+        name (str):
         agent_target_id (str):
-        metrics_config (APISchemaTestCreateRequestMetricsConfig):
-        name (Union[None, Unset, str]):
+        metrics_config (TestCreateRequestMetricsConfig):
+        label (Union[None, Unset, str]):
         initiating_agent (Union[Unset, AgentType]):  Default: AgentType.MAIHEM.
         conversation_turns_max (Union[None, Unset, int]):
         agent_maihem_behavior_prompt (Union[None, Unset, str]):
+        agent_maihem_goal_prompt (Union[None, Unset, str]):
+        agent_maihem_population_prompt (Union[None, Unset, str]):
+        documents (Union['TestCreateRequestDocumentsType0', None, Unset]):
         is_dev_mode (Union[None, Unset, bool]):  Default: False.
     """
 
-    identifier: str
+    name: str
     agent_target_id: str
-    metrics_config: "APISchemaTestCreateRequestMetricsConfig"
-    name: Union[None, Unset, str] = UNSET
+    metrics_config: "TestCreateRequestMetricsConfig"
+    label: Union[None, Unset, str] = UNSET
     initiating_agent: Union[Unset, AgentType] = AgentType.MAIHEM
     conversation_turns_max: Union[None, Unset, int] = UNSET
     agent_maihem_behavior_prompt: Union[None, Unset, str] = UNSET
+    agent_maihem_goal_prompt: Union[None, Unset, str] = UNSET
+    agent_maihem_population_prompt: Union[None, Unset, str] = UNSET
+    documents: Union["TestCreateRequestDocumentsType0", None, Unset] = UNSET
     is_dev_mode: Union[None, Unset, bool] = False
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
-        identifier = self.identifier
+        from ..models.test_create_request_documents_type_0 import TestCreateRequestDocumentsType0
+
+        name = self.name
 
         agent_target_id = self.agent_target_id
 
         metrics_config = self.metrics_config.to_dict()
 
-        name: Union[None, Unset, str]
-        if isinstance(self.name, Unset):
-            name = UNSET
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
         else:
-            name = self.name
+            label = self.label
 
         initiating_agent: Union[Unset, str] = UNSET
         if not isinstance(self.initiating_agent, Unset):
@@ -66,6 +75,26 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             agent_maihem_behavior_prompt = self.agent_maihem_behavior_prompt
 
+        agent_maihem_goal_prompt: Union[None, Unset, str]
+        if isinstance(self.agent_maihem_goal_prompt, Unset):
+            agent_maihem_goal_prompt = UNSET
+        else:
+            agent_maihem_goal_prompt = self.agent_maihem_goal_prompt
+
+        agent_maihem_population_prompt: Union[None, Unset, str]
+        if isinstance(self.agent_maihem_population_prompt, Unset):
+            agent_maihem_population_prompt = UNSET
+        else:
+            agent_maihem_population_prompt = self.agent_maihem_population_prompt
+
+        documents: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.documents, Unset):
+            documents = UNSET
+        elif isinstance(self.documents, TestCreateRequestDocumentsType0):
+            documents = self.documents.to_dict()
+        else:
+            documents = self.documents
+
         is_dev_mode: Union[None, Unset, bool]
         if isinstance(self.is_dev_mode, Unset):
             is_dev_mode = UNSET
@@ -76,19 +105,25 @@ def to_dict(self) -> Dict[str, Any]:
         field_dict.update(self.additional_properties)
         field_dict.update(
             {
-                "identifier": identifier,
+                "name": name,
                 "agent_target_id": agent_target_id,
                 "metrics_config": metrics_config,
             }
         )
-        if name is not UNSET:
-            field_dict["name"] = name
+        if label is not UNSET:
+            field_dict["label"] = label
         if initiating_agent is not UNSET:
             field_dict["initiating_agent"] = initiating_agent
         if conversation_turns_max is not UNSET:
             field_dict["conversation_turns_max"] = conversation_turns_max
         if agent_maihem_behavior_prompt is not UNSET:
             field_dict["agent_maihem_behavior_prompt"] = agent_maihem_behavior_prompt
+        if agent_maihem_goal_prompt is not UNSET:
+            field_dict["agent_maihem_goal_prompt"] = agent_maihem_goal_prompt
+        if agent_maihem_population_prompt is not UNSET:
+            field_dict["agent_maihem_population_prompt"] = agent_maihem_population_prompt
+        if documents is not UNSET:
+            field_dict["documents"] = documents
         if is_dev_mode is not UNSET:
             field_dict["is_dev_mode"] = is_dev_mode
 
@@ -96,23 +131,24 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_test_create_request_metrics_config import APISchemaTestCreateRequestMetricsConfig
+        from ..models.test_create_request_documents_type_0 import TestCreateRequestDocumentsType0
+        from ..models.test_create_request_metrics_config import TestCreateRequestMetricsConfig
 
         d = src_dict.copy()
-        identifier = d.pop("identifier")
+        name = d.pop("name")
 
         agent_target_id = d.pop("agent_target_id")
 
-        metrics_config = APISchemaTestCreateRequestMetricsConfig.from_dict(d.pop("metrics_config"))
+        metrics_config = TestCreateRequestMetricsConfig.from_dict(d.pop("metrics_config"))
 
-        def _parse_name(data: object) -> Union[None, Unset, str]:
+        def _parse_label(data: object) -> Union[None, Unset, str]:
             if data is None:
                 return data
             if isinstance(data, Unset):
                 return data
             return cast(Union[None, Unset, str], data)
 
-        name = _parse_name(d.pop("name", UNSET))
+        label = _parse_label(d.pop("label", UNSET))
 
         _initiating_agent = d.pop("initiating_agent", UNSET)
         initiating_agent: Union[Unset, AgentType]
@@ -139,6 +175,43 @@ def _parse_agent_maihem_behavior_prompt(data: object) -> Union[None, Unset, str]
 
         agent_maihem_behavior_prompt = _parse_agent_maihem_behavior_prompt(d.pop("agent_maihem_behavior_prompt", UNSET))
 
+        def _parse_agent_maihem_goal_prompt(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_maihem_goal_prompt = _parse_agent_maihem_goal_prompt(d.pop("agent_maihem_goal_prompt", UNSET))
+
+        def _parse_agent_maihem_population_prompt(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_maihem_population_prompt = _parse_agent_maihem_population_prompt(
+            d.pop("agent_maihem_population_prompt", UNSET)
+        )
+
+        def _parse_documents(data: object) -> Union["TestCreateRequestDocumentsType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                documents_type_0 = TestCreateRequestDocumentsType0.from_dict(data)
+
+                return documents_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestCreateRequestDocumentsType0", None, Unset], data)
+
+        documents = _parse_documents(d.pop("documents", UNSET))
+
         def _parse_is_dev_mode(data: object) -> Union[None, Unset, bool]:
             if data is None:
                 return data
@@ -148,19 +221,22 @@ def _parse_is_dev_mode(data: object) -> Union[None, Unset, bool]:
 
         is_dev_mode = _parse_is_dev_mode(d.pop("is_dev_mode", UNSET))
 
-        api_schema_test_create_request = cls(
-            identifier=identifier,
+        test_create_request = cls(
+            name=name,
             agent_target_id=agent_target_id,
             metrics_config=metrics_config,
-            name=name,
+            label=label,
             initiating_agent=initiating_agent,
             conversation_turns_max=conversation_turns_max,
             agent_maihem_behavior_prompt=agent_maihem_behavior_prompt,
+            agent_maihem_goal_prompt=agent_maihem_goal_prompt,
+            agent_maihem_population_prompt=agent_maihem_population_prompt,
+            documents=documents,
             is_dev_mode=is_dev_mode,
         )
 
-        api_schema_test_create_request.additional_properties = d
-        return api_schema_test_create_request
+        test_create_request.additional_properties = d
+        return test_create_request
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics_metric_summaries_type_0.py b/src/maihem/api_client/maihem_client/models/test_create_request_documents_type_0.py
similarity index 73%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics_metric_summaries_type_0.py
rename to src/maihem/api_client/maihem_client/models/test_create_request_documents_type_0.py
index 70cc6f0..6d954bb 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics_metric_summaries_type_0.py
+++ b/src/maihem/api_client/maihem_client/models/test_create_request_documents_type_0.py
@@ -3,11 +3,11 @@
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
-T = TypeVar("T", bound="APISchemaTestRunResultMetricsMetricSummariesType0")
+T = TypeVar("T", bound="TestCreateRequestDocumentsType0")
 
 
 @_attrs_define
-class APISchemaTestRunResultMetricsMetricSummariesType0:
+class TestCreateRequestDocumentsType0:
     """ """
 
     additional_properties: Dict[str, str] = _attrs_field(init=False, factory=dict)
@@ -21,10 +21,10 @@ def to_dict(self) -> Dict[str, Any]:
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
-        api_schema_test_run_result_metrics_metric_summaries_type_0 = cls()
+        test_create_request_documents_type_0 = cls()
 
-        api_schema_test_run_result_metrics_metric_summaries_type_0.additional_properties = d
-        return api_schema_test_run_result_metrics_metric_summaries_type_0
+        test_create_request_documents_type_0.additional_properties = d
+        return test_create_request_documents_type_0
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_create_request_metrics_config.py b/src/maihem/api_client/maihem_client/models/test_create_request_metrics_config.py
similarity index 76%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_create_request_metrics_config.py
rename to src/maihem/api_client/maihem_client/models/test_create_request_metrics_config.py
index bd7d0cc..a0e0008 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_create_request_metrics_config.py
+++ b/src/maihem/api_client/maihem_client/models/test_create_request_metrics_config.py
@@ -3,11 +3,11 @@
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
-T = TypeVar("T", bound="APISchemaTestCreateRequestMetricsConfig")
+T = TypeVar("T", bound="TestCreateRequestMetricsConfig")
 
 
 @_attrs_define
-class APISchemaTestCreateRequestMetricsConfig:
+class TestCreateRequestMetricsConfig:
     """ """
 
     additional_properties: Dict[str, int] = _attrs_field(init=False, factory=dict)
@@ -21,10 +21,10 @@ def to_dict(self) -> Dict[str, Any]:
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
-        api_schema_test_create_request_metrics_config = cls()
+        test_create_request_metrics_config = cls()
 
-        api_schema_test_create_request_metrics_config.additional_properties = d
-        return api_schema_test_create_request_metrics_config
+        test_create_request_metrics_config.additional_properties = d
+        return test_create_request_metrics_config
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_request_document_type_0.py b/src/maihem/api_client/maihem_client/models/test_documents_type_0.py
similarity index 72%
rename from src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_request_document_type_0.py
rename to src/maihem/api_client/maihem_client/models/test_documents_type_0.py
index 11cfe3b..0963e2d 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_conversation_turn_create_request_document_type_0.py
+++ b/src/maihem/api_client/maihem_client/models/test_documents_type_0.py
@@ -3,11 +3,11 @@
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
-T = TypeVar("T", bound="APISchemaConversationTurnCreateRequestDocumentType0")
+T = TypeVar("T", bound="TestDocumentsType0")
 
 
 @_attrs_define
-class APISchemaConversationTurnCreateRequestDocumentType0:
+class TestDocumentsType0:
     """ """
 
     additional_properties: Dict[str, str] = _attrs_field(init=False, factory=dict)
@@ -21,10 +21,10 @@ def to_dict(self) -> Dict[str, Any]:
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
-        api_schema_conversation_turn_create_request_document_type_0 = cls()
+        test_documents_type_0 = cls()
 
-        api_schema_conversation_turn_create_request_document_type_0.additional_properties = d
-        return api_schema_conversation_turn_create_request_document_type_0
+        test_documents_type_0.additional_properties = d
+        return test_documents_type_0
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_metrics_config.py b/src/maihem/api_client/maihem_client/models/test_metrics_config.py
similarity index 80%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_metrics_config.py
rename to src/maihem/api_client/maihem_client/models/test_metrics_config.py
index 55ca195..0eb9132 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_metrics_config.py
+++ b/src/maihem/api_client/maihem_client/models/test_metrics_config.py
@@ -3,11 +3,11 @@
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
-T = TypeVar("T", bound="APISchemaTestMetricsConfig")
+T = TypeVar("T", bound="TestMetricsConfig")
 
 
 @_attrs_define
-class APISchemaTestMetricsConfig:
+class TestMetricsConfig:
     """ """
 
     additional_properties: Dict[str, int] = _attrs_field(init=False, factory=dict)
@@ -21,10 +21,10 @@ def to_dict(self) -> Dict[str, Any]:
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
-        api_schema_test_metrics_config = cls()
+        test_metrics_config = cls()
 
-        api_schema_test_metrics_config.additional_properties = d
-        return api_schema_test_metrics_config
+        test_metrics_config.additional_properties = d
+        return test_metrics_config
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback.py b/src/maihem/api_client/maihem_client/models/test_result_metric_feedback.py
similarity index 62%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback.py
rename to src/maihem/api_client/maihem_client/models/test_result_metric_feedback.py
index 636d794..9803f98 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback.py
+++ b/src/maihem/api_client/maihem_client/models/test_result_metric_feedback.py
@@ -5,31 +5,35 @@
 from attrs import field as _attrs_field
 from dateutil.parser import isoparse
 
-from ..models.api_schema_test_result_metric_feedback_feedback import APISchemaTestResultMetricFeedbackFeedback
+from ..models.test_result_metric_feedback_feedback import TestResultMetricFeedbackFeedback
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="APISchemaTestResultMetricFeedback")
+T = TypeVar("T", bound="TestResultMetricFeedback")
 
 
 @_attrs_define
-class APISchemaTestResultMetricFeedback:
+class TestResultMetricFeedback:
     """
     Attributes:
         id (str):
         created_at (datetime.datetime):
         updated_at (datetime.datetime):
-        test_result_metric_id (str):
+        entity_id (str):
+        entity_type (str):
         created_by (str):
-        feedback (APISchemaTestResultMetricFeedbackFeedback):
+        feedback (TestResultMetricFeedbackFeedback):
+        test_result_metric_id (Union[None, Unset, str]):
         comments (Union[None, Unset, str]):
     """
 
     id: str
     created_at: datetime.datetime
     updated_at: datetime.datetime
-    test_result_metric_id: str
+    entity_id: str
+    entity_type: str
     created_by: str
-    feedback: APISchemaTestResultMetricFeedbackFeedback
+    feedback: TestResultMetricFeedbackFeedback
+    test_result_metric_id: Union[None, Unset, str] = UNSET
     comments: Union[None, Unset, str] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
@@ -40,12 +44,20 @@ def to_dict(self) -> Dict[str, Any]:
 
         updated_at = self.updated_at.isoformat()
 
-        test_result_metric_id = self.test_result_metric_id
+        entity_id = self.entity_id
+
+        entity_type = self.entity_type
 
         created_by = self.created_by
 
         feedback = self.feedback.value
 
+        test_result_metric_id: Union[None, Unset, str]
+        if isinstance(self.test_result_metric_id, Unset):
+            test_result_metric_id = UNSET
+        else:
+            test_result_metric_id = self.test_result_metric_id
+
         comments: Union[None, Unset, str]
         if isinstance(self.comments, Unset):
             comments = UNSET
@@ -59,11 +71,14 @@ def to_dict(self) -> Dict[str, Any]:
                 "id": id,
                 "created_at": created_at,
                 "updated_at": updated_at,
-                "test_result_metric_id": test_result_metric_id,
+                "entity_id": entity_id,
+                "entity_type": entity_type,
                 "created_by": created_by,
                 "feedback": feedback,
             }
         )
+        if test_result_metric_id is not UNSET:
+            field_dict["test_result_metric_id"] = test_result_metric_id
         if comments is not UNSET:
             field_dict["comments"] = comments
 
@@ -78,11 +93,22 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         updated_at = isoparse(d.pop("updated_at"))
 
-        test_result_metric_id = d.pop("test_result_metric_id")
+        entity_id = d.pop("entity_id")
+
+        entity_type = d.pop("entity_type")
 
         created_by = d.pop("created_by")
 
-        feedback = APISchemaTestResultMetricFeedbackFeedback(d.pop("feedback"))
+        feedback = TestResultMetricFeedbackFeedback(d.pop("feedback"))
+
+        def _parse_test_result_metric_id(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        test_result_metric_id = _parse_test_result_metric_id(d.pop("test_result_metric_id", UNSET))
 
         def _parse_comments(data: object) -> Union[None, Unset, str]:
             if data is None:
@@ -93,18 +119,20 @@ def _parse_comments(data: object) -> Union[None, Unset, str]:
 
         comments = _parse_comments(d.pop("comments", UNSET))
 
-        api_schema_test_result_metric_feedback = cls(
+        test_result_metric_feedback = cls(
             id=id,
             created_at=created_at,
             updated_at=updated_at,
-            test_result_metric_id=test_result_metric_id,
+            entity_id=entity_id,
+            entity_type=entity_type,
             created_by=created_by,
             feedback=feedback,
+            test_result_metric_id=test_result_metric_id,
             comments=comments,
         )
 
-        api_schema_test_result_metric_feedback.additional_properties = d
-        return api_schema_test_result_metric_feedback
+        test_result_metric_feedback.additional_properties = d
+        return test_result_metric_feedback
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/test_result_metric_feedback_create_request.py b/src/maihem/api_client/maihem_client/models/test_result_metric_feedback_create_request.py
new file mode 100644
index 0000000..aa7330a
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/test_result_metric_feedback_create_request.py
@@ -0,0 +1,128 @@
+from typing import Any, Dict, List, Type, TypeVar, Union, cast
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+from ..models.test_result_metric_feedback_create_request_feedback import TestResultMetricFeedbackCreateRequestFeedback
+from ..types import UNSET, Unset
+
+T = TypeVar("T", bound="TestResultMetricFeedbackCreateRequest")
+
+
+@_attrs_define
+class TestResultMetricFeedbackCreateRequest:
+    """
+    Attributes:
+        entity_id (str):
+        entity_type (str):
+        test_result_metric_id (Union[None, Unset, str]):
+        feedback (Union[Unset, TestResultMetricFeedbackCreateRequestFeedback]):  Default:
+            TestResultMetricFeedbackCreateRequestFeedback.POSITIVE.
+        comments (Union[None, Unset, str]):
+    """
+
+    entity_id: str
+    entity_type: str
+    test_result_metric_id: Union[None, Unset, str] = UNSET
+    feedback: Union[Unset, TestResultMetricFeedbackCreateRequestFeedback] = (
+        TestResultMetricFeedbackCreateRequestFeedback.POSITIVE
+    )
+    comments: Union[None, Unset, str] = UNSET
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        entity_id = self.entity_id
+
+        entity_type = self.entity_type
+
+        test_result_metric_id: Union[None, Unset, str]
+        if isinstance(self.test_result_metric_id, Unset):
+            test_result_metric_id = UNSET
+        else:
+            test_result_metric_id = self.test_result_metric_id
+
+        feedback: Union[Unset, str] = UNSET
+        if not isinstance(self.feedback, Unset):
+            feedback = self.feedback.value
+
+        comments: Union[None, Unset, str]
+        if isinstance(self.comments, Unset):
+            comments = UNSET
+        else:
+            comments = self.comments
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "entity_id": entity_id,
+                "entity_type": entity_type,
+            }
+        )
+        if test_result_metric_id is not UNSET:
+            field_dict["test_result_metric_id"] = test_result_metric_id
+        if feedback is not UNSET:
+            field_dict["feedback"] = feedback
+        if comments is not UNSET:
+            field_dict["comments"] = comments
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        d = src_dict.copy()
+        entity_id = d.pop("entity_id")
+
+        entity_type = d.pop("entity_type")
+
+        def _parse_test_result_metric_id(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        test_result_metric_id = _parse_test_result_metric_id(d.pop("test_result_metric_id", UNSET))
+
+        _feedback = d.pop("feedback", UNSET)
+        feedback: Union[Unset, TestResultMetricFeedbackCreateRequestFeedback]
+        if isinstance(_feedback, Unset):
+            feedback = UNSET
+        else:
+            feedback = TestResultMetricFeedbackCreateRequestFeedback(_feedback)
+
+        def _parse_comments(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        comments = _parse_comments(d.pop("comments", UNSET))
+
+        test_result_metric_feedback_create_request = cls(
+            entity_id=entity_id,
+            entity_type=entity_type,
+            test_result_metric_id=test_result_metric_id,
+            feedback=feedback,
+            comments=comments,
+        )
+
+        test_result_metric_feedback_create_request.additional_properties = d
+        return test_result_metric_feedback_create_request
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_create_request_feedback.py b/src/maihem/api_client/maihem_client/models/test_result_metric_feedback_create_request_feedback.py
similarity index 65%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_create_request_feedback.py
rename to src/maihem/api_client/maihem_client/models/test_result_metric_feedback_create_request_feedback.py
index 0696baf..337c970 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_create_request_feedback.py
+++ b/src/maihem/api_client/maihem_client/models/test_result_metric_feedback_create_request_feedback.py
@@ -1,7 +1,7 @@
 from enum import Enum
 
 
-class APISchemaTestResultMetricFeedbackCreateRequestFeedback(str, Enum):
+class TestResultMetricFeedbackCreateRequestFeedback(str, Enum):
     NEGATIVE = "negative"
     POSITIVE = "positive"
 
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_feedback.py b/src/maihem/api_client/maihem_client/models/test_result_metric_feedback_feedback.py
similarity index 69%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_feedback.py
rename to src/maihem/api_client/maihem_client/models/test_result_metric_feedback_feedback.py
index 674f0ff..e653cbc 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_result_metric_feedback_feedback.py
+++ b/src/maihem/api_client/maihem_client/models/test_result_metric_feedback_feedback.py
@@ -1,7 +1,7 @@
 from enum import Enum
 
 
-class APISchemaTestResultMetricFeedbackFeedback(str, Enum):
+class TestResultMetricFeedbackFeedback(str, Enum):
     NEGATIVE = "negative"
     POSITIVE = "positive"
 
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run.py b/src/maihem/api_client/maihem_client/models/test_run.py
similarity index 61%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run.py
rename to src/maihem/api_client/maihem_client/models/test_run.py
index f76d80d..ac3c8cb 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run.py
+++ b/src/maihem/api_client/maihem_client/models/test_run.py
@@ -10,42 +10,58 @@
 from ..types import UNSET, Unset
 
 if TYPE_CHECKING:
-    from ..models.api_schema_links import APISchemaLinks
+    from ..models.links import Links
 
 
-T = TypeVar("T", bound="APISchemaTestRun")
+T = TypeVar("T", bound="TestRun")
 
 
 @_attrs_define
-class APISchemaTestRun:
+class TestRun:
     """
     Attributes:
         id (str):
         created_at (datetime.datetime):
         updated_at (datetime.datetime):
+        name (str):
         test_id (str):
+        test_name (str):
+        agent_target_id (str):
+        agent_target_name (str):
         status (TestStatusEnum):
+        label (Union[None, Unset, str]):
+        test_label (Union[None, Unset, str]):
+        agent_target_label (Union[None, Unset, str]):
         started_at (Union[None, Unset, datetime.datetime]):
         completed_at (Union[None, Unset, datetime.datetime]):
         result (Union[None, TestResultEnum, Unset]):
         result_score (Union[None, Unset, float]):
-        links (Union['APISchemaLinks', None, Unset]):
+        result_score_change (Union[None, Unset, float]):
+        links (Union['Links', None, Unset]):
     """
 
     id: str
     created_at: datetime.datetime
     updated_at: datetime.datetime
+    name: str
     test_id: str
+    test_name: str
+    agent_target_id: str
+    agent_target_name: str
     status: TestStatusEnum
+    label: Union[None, Unset, str] = UNSET
+    test_label: Union[None, Unset, str] = UNSET
+    agent_target_label: Union[None, Unset, str] = UNSET
     started_at: Union[None, Unset, datetime.datetime] = UNSET
     completed_at: Union[None, Unset, datetime.datetime] = UNSET
     result: Union[None, TestResultEnum, Unset] = UNSET
     result_score: Union[None, Unset, float] = UNSET
-    links: Union["APISchemaLinks", None, Unset] = UNSET
+    result_score_change: Union[None, Unset, float] = UNSET
+    links: Union["Links", None, Unset] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
-        from ..models.api_schema_links import APISchemaLinks
+        from ..models.links import Links
 
         id = self.id
 
@@ -53,10 +69,36 @@ def to_dict(self) -> Dict[str, Any]:
 
         updated_at = self.updated_at.isoformat()
 
+        name = self.name
+
         test_id = self.test_id
 
+        test_name = self.test_name
+
+        agent_target_id = self.agent_target_id
+
+        agent_target_name = self.agent_target_name
+
         status = self.status.value
 
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
+        else:
+            label = self.label
+
+        test_label: Union[None, Unset, str]
+        if isinstance(self.test_label, Unset):
+            test_label = UNSET
+        else:
+            test_label = self.test_label
+
+        agent_target_label: Union[None, Unset, str]
+        if isinstance(self.agent_target_label, Unset):
+            agent_target_label = UNSET
+        else:
+            agent_target_label = self.agent_target_label
+
         started_at: Union[None, Unset, str]
         if isinstance(self.started_at, Unset):
             started_at = UNSET
@@ -87,10 +129,16 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             result_score = self.result_score
 
+        result_score_change: Union[None, Unset, float]
+        if isinstance(self.result_score_change, Unset):
+            result_score_change = UNSET
+        else:
+            result_score_change = self.result_score_change
+
         links: Union[Dict[str, Any], None, Unset]
         if isinstance(self.links, Unset):
             links = UNSET
-        elif isinstance(self.links, APISchemaLinks):
+        elif isinstance(self.links, Links):
             links = self.links.to_dict()
         else:
             links = self.links
@@ -102,10 +150,20 @@ def to_dict(self) -> Dict[str, Any]:
                 "id": id,
                 "created_at": created_at,
                 "updated_at": updated_at,
+                "name": name,
                 "test_id": test_id,
+                "test_name": test_name,
+                "agent_target_id": agent_target_id,
+                "agent_target_name": agent_target_name,
                 "status": status,
             }
         )
+        if label is not UNSET:
+            field_dict["label"] = label
+        if test_label is not UNSET:
+            field_dict["test_label"] = test_label
+        if agent_target_label is not UNSET:
+            field_dict["agent_target_label"] = agent_target_label
         if started_at is not UNSET:
             field_dict["started_at"] = started_at
         if completed_at is not UNSET:
@@ -114,6 +172,8 @@ def to_dict(self) -> Dict[str, Any]:
             field_dict["result"] = result
         if result_score is not UNSET:
             field_dict["result_score"] = result_score
+        if result_score_change is not UNSET:
+            field_dict["result_score_change"] = result_score_change
         if links is not UNSET:
             field_dict["links"] = links
 
@@ -121,7 +181,7 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_links import APISchemaLinks
+        from ..models.links import Links
 
         d = src_dict.copy()
         id = d.pop("id")
@@ -130,10 +190,45 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         updated_at = isoparse(d.pop("updated_at"))
 
+        name = d.pop("name")
+
         test_id = d.pop("test_id")
 
+        test_name = d.pop("test_name")
+
+        agent_target_id = d.pop("agent_target_id")
+
+        agent_target_name = d.pop("agent_target_name")
+
         status = TestStatusEnum(d.pop("status"))
 
+        def _parse_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        label = _parse_label(d.pop("label", UNSET))
+
+        def _parse_test_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        test_label = _parse_test_label(d.pop("test_label", UNSET))
+
+        def _parse_agent_target_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_target_label = _parse_agent_target_label(d.pop("agent_target_label", UNSET))
+
         def _parse_started_at(data: object) -> Union[None, Unset, datetime.datetime]:
             if data is None:
                 return data
@@ -194,7 +289,16 @@ def _parse_result_score(data: object) -> Union[None, Unset, float]:
 
         result_score = _parse_result_score(d.pop("result_score", UNSET))
 
-        def _parse_links(data: object) -> Union["APISchemaLinks", None, Unset]:
+        def _parse_result_score_change(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        result_score_change = _parse_result_score_change(d.pop("result_score_change", UNSET))
+
+        def _parse_links(data: object) -> Union["Links", None, Unset]:
             if data is None:
                 return data
             if isinstance(data, Unset):
@@ -202,30 +306,38 @@ def _parse_links(data: object) -> Union["APISchemaLinks", None, Unset]:
             try:
                 if not isinstance(data, dict):
                     raise TypeError()
-                links_type_0 = APISchemaLinks.from_dict(data)
+                links_type_0 = Links.from_dict(data)
 
                 return links_type_0
             except:  # noqa: E722
                 pass
-            return cast(Union["APISchemaLinks", None, Unset], data)
+            return cast(Union["Links", None, Unset], data)
 
         links = _parse_links(d.pop("links", UNSET))
 
-        api_schema_test_run = cls(
+        test_run = cls(
             id=id,
             created_at=created_at,
             updated_at=updated_at,
+            name=name,
             test_id=test_id,
+            test_name=test_name,
+            agent_target_id=agent_target_id,
+            agent_target_name=agent_target_name,
             status=status,
+            label=label,
+            test_label=test_label,
+            agent_target_label=agent_target_label,
             started_at=started_at,
             completed_at=completed_at,
             result=result,
             result_score=result_score,
+            result_score_change=result_score_change,
             links=links,
         )
 
-        api_schema_test_run.additional_properties = d
-        return api_schema_test_run
+        test_run.additional_properties = d
+        return test_run
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_conversations.py b/src/maihem/api_client/maihem_client/models/test_run_conversation_i_ds.py
similarity index 62%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run_conversations.py
rename to src/maihem/api_client/maihem_client/models/test_run_conversation_i_ds.py
index a50256f..f743aac 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_conversations.py
+++ b/src/maihem/api_client/maihem_client/models/test_run_conversation_i_ds.py
@@ -10,44 +10,60 @@
 from ..types import UNSET, Unset
 
 if TYPE_CHECKING:
-    from ..models.api_schema_links import APISchemaLinks
+    from ..models.links import Links
 
 
-T = TypeVar("T", bound="APISchemaTestRunConversations")
+T = TypeVar("T", bound="TestRunConversationIDs")
 
 
 @_attrs_define
-class APISchemaTestRunConversations:
+class TestRunConversationIDs:
     """
     Attributes:
         id (str):
         created_at (datetime.datetime):
         updated_at (datetime.datetime):
+        name (str):
         test_id (str):
+        test_name (str):
+        agent_target_id (str):
+        agent_target_name (str):
         status (TestStatusEnum):
+        label (Union[None, Unset, str]):
+        test_label (Union[None, Unset, str]):
+        agent_target_label (Union[None, Unset, str]):
         started_at (Union[None, Unset, datetime.datetime]):
         completed_at (Union[None, Unset, datetime.datetime]):
         result (Union[None, TestResultEnum, Unset]):
         result_score (Union[None, Unset, float]):
-        links (Union['APISchemaLinks', None, Unset]):
+        result_score_change (Union[None, Unset, float]):
+        links (Union['Links', None, Unset]):
         conversation_ids (Union[Unset, List[str]]):
     """
 
     id: str
     created_at: datetime.datetime
     updated_at: datetime.datetime
+    name: str
     test_id: str
+    test_name: str
+    agent_target_id: str
+    agent_target_name: str
     status: TestStatusEnum
+    label: Union[None, Unset, str] = UNSET
+    test_label: Union[None, Unset, str] = UNSET
+    agent_target_label: Union[None, Unset, str] = UNSET
     started_at: Union[None, Unset, datetime.datetime] = UNSET
     completed_at: Union[None, Unset, datetime.datetime] = UNSET
     result: Union[None, TestResultEnum, Unset] = UNSET
     result_score: Union[None, Unset, float] = UNSET
-    links: Union["APISchemaLinks", None, Unset] = UNSET
+    result_score_change: Union[None, Unset, float] = UNSET
+    links: Union["Links", None, Unset] = UNSET
     conversation_ids: Union[Unset, List[str]] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
-        from ..models.api_schema_links import APISchemaLinks
+        from ..models.links import Links
 
         id = self.id
 
@@ -55,10 +71,36 @@ def to_dict(self) -> Dict[str, Any]:
 
         updated_at = self.updated_at.isoformat()
 
+        name = self.name
+
         test_id = self.test_id
 
+        test_name = self.test_name
+
+        agent_target_id = self.agent_target_id
+
+        agent_target_name = self.agent_target_name
+
         status = self.status.value
 
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
+        else:
+            label = self.label
+
+        test_label: Union[None, Unset, str]
+        if isinstance(self.test_label, Unset):
+            test_label = UNSET
+        else:
+            test_label = self.test_label
+
+        agent_target_label: Union[None, Unset, str]
+        if isinstance(self.agent_target_label, Unset):
+            agent_target_label = UNSET
+        else:
+            agent_target_label = self.agent_target_label
+
         started_at: Union[None, Unset, str]
         if isinstance(self.started_at, Unset):
             started_at = UNSET
@@ -89,10 +131,16 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             result_score = self.result_score
 
+        result_score_change: Union[None, Unset, float]
+        if isinstance(self.result_score_change, Unset):
+            result_score_change = UNSET
+        else:
+            result_score_change = self.result_score_change
+
         links: Union[Dict[str, Any], None, Unset]
         if isinstance(self.links, Unset):
             links = UNSET
-        elif isinstance(self.links, APISchemaLinks):
+        elif isinstance(self.links, Links):
             links = self.links.to_dict()
         else:
             links = self.links
@@ -108,10 +156,20 @@ def to_dict(self) -> Dict[str, Any]:
                 "id": id,
                 "created_at": created_at,
                 "updated_at": updated_at,
+                "name": name,
                 "test_id": test_id,
+                "test_name": test_name,
+                "agent_target_id": agent_target_id,
+                "agent_target_name": agent_target_name,
                 "status": status,
             }
         )
+        if label is not UNSET:
+            field_dict["label"] = label
+        if test_label is not UNSET:
+            field_dict["test_label"] = test_label
+        if agent_target_label is not UNSET:
+            field_dict["agent_target_label"] = agent_target_label
         if started_at is not UNSET:
             field_dict["started_at"] = started_at
         if completed_at is not UNSET:
@@ -120,6 +178,8 @@ def to_dict(self) -> Dict[str, Any]:
             field_dict["result"] = result
         if result_score is not UNSET:
             field_dict["result_score"] = result_score
+        if result_score_change is not UNSET:
+            field_dict["result_score_change"] = result_score_change
         if links is not UNSET:
             field_dict["links"] = links
         if conversation_ids is not UNSET:
@@ -129,7 +189,7 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_links import APISchemaLinks
+        from ..models.links import Links
 
         d = src_dict.copy()
         id = d.pop("id")
@@ -138,10 +198,45 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         updated_at = isoparse(d.pop("updated_at"))
 
+        name = d.pop("name")
+
         test_id = d.pop("test_id")
 
+        test_name = d.pop("test_name")
+
+        agent_target_id = d.pop("agent_target_id")
+
+        agent_target_name = d.pop("agent_target_name")
+
         status = TestStatusEnum(d.pop("status"))
 
+        def _parse_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        label = _parse_label(d.pop("label", UNSET))
+
+        def _parse_test_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        test_label = _parse_test_label(d.pop("test_label", UNSET))
+
+        def _parse_agent_target_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_target_label = _parse_agent_target_label(d.pop("agent_target_label", UNSET))
+
         def _parse_started_at(data: object) -> Union[None, Unset, datetime.datetime]:
             if data is None:
                 return data
@@ -202,7 +297,16 @@ def _parse_result_score(data: object) -> Union[None, Unset, float]:
 
         result_score = _parse_result_score(d.pop("result_score", UNSET))
 
-        def _parse_links(data: object) -> Union["APISchemaLinks", None, Unset]:
+        def _parse_result_score_change(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        result_score_change = _parse_result_score_change(d.pop("result_score_change", UNSET))
+
+        def _parse_links(data: object) -> Union["Links", None, Unset]:
             if data is None:
                 return data
             if isinstance(data, Unset):
@@ -210,33 +314,41 @@ def _parse_links(data: object) -> Union["APISchemaLinks", None, Unset]:
             try:
                 if not isinstance(data, dict):
                     raise TypeError()
-                links_type_0 = APISchemaLinks.from_dict(data)
+                links_type_0 = Links.from_dict(data)
 
                 return links_type_0
             except:  # noqa: E722
                 pass
-            return cast(Union["APISchemaLinks", None, Unset], data)
+            return cast(Union["Links", None, Unset], data)
 
         links = _parse_links(d.pop("links", UNSET))
 
         conversation_ids = cast(List[str], d.pop("conversation_ids", UNSET))
 
-        api_schema_test_run_conversations = cls(
+        test_run_conversation_i_ds = cls(
             id=id,
             created_at=created_at,
             updated_at=updated_at,
+            name=name,
             test_id=test_id,
+            test_name=test_name,
+            agent_target_id=agent_target_id,
+            agent_target_name=agent_target_name,
             status=status,
+            label=label,
+            test_label=test_label,
+            agent_target_label=agent_target_label,
             started_at=started_at,
             completed_at=completed_at,
             result=result,
             result_score=result_score,
+            result_score_change=result_score_change,
             links=links,
             conversation_ids=conversation_ids,
         )
 
-        api_schema_test_run_conversations.additional_properties = d
-        return api_schema_test_run_conversations
+        test_run_conversation_i_ds.additional_properties = d
+        return test_run_conversation_i_ds
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_conversation_scores.py b/src/maihem/api_client/maihem_client/models/test_run_conversation_scores.py
similarity index 72%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run_conversation_scores.py
rename to src/maihem/api_client/maihem_client/models/test_run_conversation_scores.py
index 9e6a6ad..b4d26b3 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_conversation_scores.py
+++ b/src/maihem/api_client/maihem_client/models/test_run_conversation_scores.py
@@ -1,15 +1,13 @@
-from typing import Any, Dict, List, Type, TypeVar, Union, cast
+from typing import Any, Dict, List, Type, TypeVar
 
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
-from ..types import UNSET, Unset
-
-T = TypeVar("T", bound="APISchemaTestRunConversationScores")
+T = TypeVar("T", bound="TestRunConversationScores")
 
 
 @_attrs_define
-class APISchemaTestRunConversationScores:
+class TestRunConversationScores:
     """
     Attributes:
         total_conversations (int):
@@ -20,7 +18,7 @@ class APISchemaTestRunConversationScores:
         status_running (int):
         status_pending (int):
         status_paused (int):
-        total_score (Union[None, Unset, float]):
+        status_canceled (int):
     """
 
     total_conversations: int
@@ -31,7 +29,7 @@ class APISchemaTestRunConversationScores:
     status_running: int
     status_pending: int
     status_paused: int
-    total_score: Union[None, Unset, float] = UNSET
+    status_canceled: int
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
@@ -51,11 +49,7 @@ def to_dict(self) -> Dict[str, Any]:
 
         status_paused = self.status_paused
 
-        total_score: Union[None, Unset, float]
-        if isinstance(self.total_score, Unset):
-            total_score = UNSET
-        else:
-            total_score = self.total_score
+        status_canceled = self.status_canceled
 
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
@@ -69,10 +63,9 @@ def to_dict(self) -> Dict[str, Any]:
                 "status_running": status_running,
                 "status_pending": status_pending,
                 "status_paused": status_paused,
+                "status_canceled": status_canceled,
             }
         )
-        if total_score is not UNSET:
-            field_dict["total_score"] = total_score
 
         return field_dict
 
@@ -95,16 +88,9 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         status_paused = d.pop("status_paused")
 
-        def _parse_total_score(data: object) -> Union[None, Unset, float]:
-            if data is None:
-                return data
-            if isinstance(data, Unset):
-                return data
-            return cast(Union[None, Unset, float], data)
-
-        total_score = _parse_total_score(d.pop("total_score", UNSET))
+        status_canceled = d.pop("status_canceled")
 
-        api_schema_test_run_conversation_scores = cls(
+        test_run_conversation_scores = cls(
             total_conversations=total_conversations,
             result_passed=result_passed,
             result_failed=result_failed,
@@ -113,11 +99,11 @@ def _parse_total_score(data: object) -> Union[None, Unset, float]:
             status_running=status_running,
             status_pending=status_pending,
             status_paused=status_paused,
-            total_score=total_score,
+            status_canceled=status_canceled,
         )
 
-        api_schema_test_run_conversation_scores.additional_properties = d
-        return api_schema_test_run_conversation_scores
+        test_run_conversation_scores.additional_properties = d
+        return test_run_conversation_scores
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metric_scores.py b/src/maihem/api_client/maihem_client/models/test_run_metric_scores.py
similarity index 54%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metric_scores.py
rename to src/maihem/api_client/maihem_client/models/test_run_metric_scores.py
index d8cff62..b627d29 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metric_scores.py
+++ b/src/maihem/api_client/maihem_client/models/test_run_metric_scores.py
@@ -1,16 +1,21 @@
-from typing import Any, Dict, List, Type, TypeVar, Union, cast
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar, Union, cast
 
 from attrs import define as _attrs_define
 from attrs import field as _attrs_field
 
 from ..models.test_result_enum import TestResultEnum
+from ..models.test_status_enum import TestStatusEnum
 from ..types import UNSET, Unset
 
-T = TypeVar("T", bound="APISchemaTestRunResultMetricScores")
+if TYPE_CHECKING:
+    from ..models.test_run_metric_scores_criteria_failures_type_0 import TestRunMetricScoresCriteriaFailuresType0
+
+
+T = TypeVar("T", bound="TestRunMetricScores")
 
 
 @_attrs_define
-class APISchemaTestRunResultMetricScores:
+class TestRunMetricScores:
     """
     Attributes:
         total_conversations (int):
@@ -21,8 +26,13 @@ class APISchemaTestRunResultMetricScores:
         status_running (int):
         status_pending (int):
         status_paused (int):
-        result (Union[None, TestResultEnum, Unset]):
+        status_canceled (int):
+        status (TestStatusEnum):
         total_score (Union[None, Unset, float]):
+        total_score_change (Union[None, Unset, float]):
+        result (Union[None, TestResultEnum, Unset]):
+        summary (Union[None, Unset, str]):
+        criteria_failures (Union['TestRunMetricScoresCriteriaFailuresType0', None, Unset]):
     """
 
     total_conversations: int
@@ -33,11 +43,18 @@ class APISchemaTestRunResultMetricScores:
     status_running: int
     status_pending: int
     status_paused: int
-    result: Union[None, TestResultEnum, Unset] = UNSET
+    status_canceled: int
+    status: TestStatusEnum
     total_score: Union[None, Unset, float] = UNSET
+    total_score_change: Union[None, Unset, float] = UNSET
+    result: Union[None, TestResultEnum, Unset] = UNSET
+    summary: Union[None, Unset, str] = UNSET
+    criteria_failures: Union["TestRunMetricScoresCriteriaFailuresType0", None, Unset] = UNSET
     additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
+        from ..models.test_run_metric_scores_criteria_failures_type_0 import TestRunMetricScoresCriteriaFailuresType0
+
         total_conversations = self.total_conversations
 
         result_passed = self.result_passed
@@ -54,6 +71,22 @@ def to_dict(self) -> Dict[str, Any]:
 
         status_paused = self.status_paused
 
+        status_canceled = self.status_canceled
+
+        status = self.status.value
+
+        total_score: Union[None, Unset, float]
+        if isinstance(self.total_score, Unset):
+            total_score = UNSET
+        else:
+            total_score = self.total_score
+
+        total_score_change: Union[None, Unset, float]
+        if isinstance(self.total_score_change, Unset):
+            total_score_change = UNSET
+        else:
+            total_score_change = self.total_score_change
+
         result: Union[None, Unset, str]
         if isinstance(self.result, Unset):
             result = UNSET
@@ -62,11 +95,19 @@ def to_dict(self) -> Dict[str, Any]:
         else:
             result = self.result
 
-        total_score: Union[None, Unset, float]
-        if isinstance(self.total_score, Unset):
-            total_score = UNSET
+        summary: Union[None, Unset, str]
+        if isinstance(self.summary, Unset):
+            summary = UNSET
         else:
-            total_score = self.total_score
+            summary = self.summary
+
+        criteria_failures: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.criteria_failures, Unset):
+            criteria_failures = UNSET
+        elif isinstance(self.criteria_failures, TestRunMetricScoresCriteriaFailuresType0):
+            criteria_failures = self.criteria_failures.to_dict()
+        else:
+            criteria_failures = self.criteria_failures
 
         field_dict: Dict[str, Any] = {}
         field_dict.update(self.additional_properties)
@@ -80,17 +121,27 @@ def to_dict(self) -> Dict[str, Any]:
                 "status_running": status_running,
                 "status_pending": status_pending,
                 "status_paused": status_paused,
+                "status_canceled": status_canceled,
+                "status": status,
             }
         )
-        if result is not UNSET:
-            field_dict["result"] = result
         if total_score is not UNSET:
             field_dict["total_score"] = total_score
+        if total_score_change is not UNSET:
+            field_dict["total_score_change"] = total_score_change
+        if result is not UNSET:
+            field_dict["result"] = result
+        if summary is not UNSET:
+            field_dict["summary"] = summary
+        if criteria_failures is not UNSET:
+            field_dict["criteria_failures"] = criteria_failures
 
         return field_dict
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.test_run_metric_scores_criteria_failures_type_0 import TestRunMetricScoresCriteriaFailuresType0
+
         d = src_dict.copy()
         total_conversations = d.pop("total_conversations")
 
@@ -108,6 +159,28 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
 
         status_paused = d.pop("status_paused")
 
+        status_canceled = d.pop("status_canceled")
+
+        status = TestStatusEnum(d.pop("status"))
+
+        def _parse_total_score(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        total_score = _parse_total_score(d.pop("total_score", UNSET))
+
+        def _parse_total_score_change(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        total_score_change = _parse_total_score_change(d.pop("total_score_change", UNSET))
+
         def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
             if data is None:
                 return data
@@ -125,16 +198,33 @@ def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
 
         result = _parse_result(d.pop("result", UNSET))
 
-        def _parse_total_score(data: object) -> Union[None, Unset, float]:
+        def _parse_summary(data: object) -> Union[None, Unset, str]:
             if data is None:
                 return data
             if isinstance(data, Unset):
                 return data
-            return cast(Union[None, Unset, float], data)
+            return cast(Union[None, Unset, str], data)
 
-        total_score = _parse_total_score(d.pop("total_score", UNSET))
+        summary = _parse_summary(d.pop("summary", UNSET))
 
-        api_schema_test_run_result_metric_scores = cls(
+        def _parse_criteria_failures(data: object) -> Union["TestRunMetricScoresCriteriaFailuresType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                criteria_failures_type_0 = TestRunMetricScoresCriteriaFailuresType0.from_dict(data)
+
+                return criteria_failures_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunMetricScoresCriteriaFailuresType0", None, Unset], data)
+
+        criteria_failures = _parse_criteria_failures(d.pop("criteria_failures", UNSET))
+
+        test_run_metric_scores = cls(
             total_conversations=total_conversations,
             result_passed=result_passed,
             result_failed=result_failed,
@@ -143,12 +233,17 @@ def _parse_total_score(data: object) -> Union[None, Unset, float]:
             status_running=status_running,
             status_pending=status_pending,
             status_paused=status_paused,
-            result=result,
+            status_canceled=status_canceled,
+            status=status,
             total_score=total_score,
+            total_score_change=total_score_change,
+            result=result,
+            summary=summary,
+            criteria_failures=criteria_failures,
         )
 
-        api_schema_test_run_result_metric_scores.additional_properties = d
-        return api_schema_test_run_result_metric_scores
+        test_run_metric_scores.additional_properties = d
+        return test_run_metric_scores
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics_metric_scores_type_0.py b/src/maihem/api_client/maihem_client/models/test_run_metric_scores_criteria_failures_type_0.py
similarity index 53%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics_metric_scores_type_0.py
rename to src/maihem/api_client/maihem_client/models/test_run_metric_scores_criteria_failures_type_0.py
index 9c26d95..4ee0e28 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_metrics_metric_scores_type_0.py
+++ b/src/maihem/api_client/maihem_client/models/test_run_metric_scores_criteria_failures_type_0.py
@@ -4,17 +4,17 @@
 from attrs import field as _attrs_field
 
 if TYPE_CHECKING:
-    from ..models.api_schema_test_run_result_metric_scores import APISchemaTestRunResultMetricScores
+    from ..models.criteria_instance_base import CriteriaInstanceBase
 
 
-T = TypeVar("T", bound="APISchemaTestRunResultMetricsMetricScoresType0")
+T = TypeVar("T", bound="TestRunMetricScoresCriteriaFailuresType0")
 
 
 @_attrs_define
-class APISchemaTestRunResultMetricsMetricScoresType0:
+class TestRunMetricScoresCriteriaFailuresType0:
     """ """
 
-    additional_properties: Dict[str, "APISchemaTestRunResultMetricScores"] = _attrs_field(init=False, factory=dict)
+    additional_properties: Dict[str, "CriteriaInstanceBase"] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
         field_dict: Dict[str, Any] = {}
@@ -25,28 +25,28 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_test_run_result_metric_scores import APISchemaTestRunResultMetricScores
+        from ..models.criteria_instance_base import CriteriaInstanceBase
 
         d = src_dict.copy()
-        api_schema_test_run_result_metrics_metric_scores_type_0 = cls()
+        test_run_metric_scores_criteria_failures_type_0 = cls()
 
         additional_properties = {}
         for prop_name, prop_dict in d.items():
-            additional_property = APISchemaTestRunResultMetricScores.from_dict(prop_dict)
+            additional_property = CriteriaInstanceBase.from_dict(prop_dict)
 
             additional_properties[prop_name] = additional_property
 
-        api_schema_test_run_result_metrics_metric_scores_type_0.additional_properties = additional_properties
-        return api_schema_test_run_result_metrics_metric_scores_type_0
+        test_run_metric_scores_criteria_failures_type_0.additional_properties = additional_properties
+        return test_run_metric_scores_criteria_failures_type_0
 
     @property
     def additional_keys(self) -> List[str]:
         return list(self.additional_properties.keys())
 
-    def __getitem__(self, key: str) -> "APISchemaTestRunResultMetricScores":
+    def __getitem__(self, key: str) -> "CriteriaInstanceBase":
         return self.additional_properties[key]
 
-    def __setitem__(self, key: str, value: "APISchemaTestRunResultMetricScores") -> None:
+    def __setitem__(self, key: str, value: "CriteriaInstanceBase") -> None:
         self.additional_properties[key] = value
 
     def __delitem__(self, key: str) -> None:
diff --git a/src/maihem/api_client/maihem_client/models/test_run_results.py b/src/maihem/api_client/maihem_client/models/test_run_results.py
new file mode 100644
index 0000000..228bd64
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/test_run_results.py
@@ -0,0 +1,488 @@
+import datetime
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar, Union, cast
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+from dateutil.parser import isoparse
+
+from ..models.test_result_enum import TestResultEnum
+from ..models.test_status_enum import TestStatusEnum
+from ..types import UNSET, Unset
+
+if TYPE_CHECKING:
+    from ..models.links import Links
+    from ..models.test_run_conversation_scores import TestRunConversationScores
+    from ..models.test_run_results_metric_scores_type_0 import TestRunResultsMetricScoresType0
+    from ..models.test_run_results_module_group_scores_type_0 import TestRunResultsModuleGroupScoresType0
+    from ..models.test_run_results_module_scores_type_0 import TestRunResultsModuleScoresType0
+
+
+T = TypeVar("T", bound="TestRunResults")
+
+
+@_attrs_define
+class TestRunResults:
+    """
+    Attributes:
+        id (str):
+        created_at (datetime.datetime):
+        updated_at (datetime.datetime):
+        name (str):
+        test_id (str):
+        test_name (str):
+        agent_target_id (str):
+        agent_target_name (str):
+        status (TestStatusEnum):
+        label (Union[None, Unset, str]):
+        test_label (Union[None, Unset, str]):
+        agent_target_label (Union[None, Unset, str]):
+        started_at (Union[None, Unset, datetime.datetime]):
+        completed_at (Union[None, Unset, datetime.datetime]):
+        result (Union[None, TestResultEnum, Unset]):
+        result_score (Union[None, Unset, float]):
+        result_score_change (Union[None, Unset, float]):
+        links (Union['Links', None, Unset]):
+        conversation_scores (Union['TestRunConversationScores', None, Unset]):
+        metric_scores (Union['TestRunResultsMetricScoresType0', None, Unset]):
+        module_scores (Union['TestRunResultsModuleScoresType0', None, Unset]):
+        module_group_scores (Union['TestRunResultsModuleGroupScoresType0', None, Unset]):
+    """
+
+    id: str
+    created_at: datetime.datetime
+    updated_at: datetime.datetime
+    name: str
+    test_id: str
+    test_name: str
+    agent_target_id: str
+    agent_target_name: str
+    status: TestStatusEnum
+    label: Union[None, Unset, str] = UNSET
+    test_label: Union[None, Unset, str] = UNSET
+    agent_target_label: Union[None, Unset, str] = UNSET
+    started_at: Union[None, Unset, datetime.datetime] = UNSET
+    completed_at: Union[None, Unset, datetime.datetime] = UNSET
+    result: Union[None, TestResultEnum, Unset] = UNSET
+    result_score: Union[None, Unset, float] = UNSET
+    result_score_change: Union[None, Unset, float] = UNSET
+    links: Union["Links", None, Unset] = UNSET
+    conversation_scores: Union["TestRunConversationScores", None, Unset] = UNSET
+    metric_scores: Union["TestRunResultsMetricScoresType0", None, Unset] = UNSET
+    module_scores: Union["TestRunResultsModuleScoresType0", None, Unset] = UNSET
+    module_group_scores: Union["TestRunResultsModuleGroupScoresType0", None, Unset] = UNSET
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        from ..models.links import Links
+        from ..models.test_run_conversation_scores import TestRunConversationScores
+        from ..models.test_run_results_metric_scores_type_0 import TestRunResultsMetricScoresType0
+        from ..models.test_run_results_module_group_scores_type_0 import TestRunResultsModuleGroupScoresType0
+        from ..models.test_run_results_module_scores_type_0 import TestRunResultsModuleScoresType0
+
+        id = self.id
+
+        created_at = self.created_at.isoformat()
+
+        updated_at = self.updated_at.isoformat()
+
+        name = self.name
+
+        test_id = self.test_id
+
+        test_name = self.test_name
+
+        agent_target_id = self.agent_target_id
+
+        agent_target_name = self.agent_target_name
+
+        status = self.status.value
+
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
+        else:
+            label = self.label
+
+        test_label: Union[None, Unset, str]
+        if isinstance(self.test_label, Unset):
+            test_label = UNSET
+        else:
+            test_label = self.test_label
+
+        agent_target_label: Union[None, Unset, str]
+        if isinstance(self.agent_target_label, Unset):
+            agent_target_label = UNSET
+        else:
+            agent_target_label = self.agent_target_label
+
+        started_at: Union[None, Unset, str]
+        if isinstance(self.started_at, Unset):
+            started_at = UNSET
+        elif isinstance(self.started_at, datetime.datetime):
+            started_at = self.started_at.isoformat()
+        else:
+            started_at = self.started_at
+
+        completed_at: Union[None, Unset, str]
+        if isinstance(self.completed_at, Unset):
+            completed_at = UNSET
+        elif isinstance(self.completed_at, datetime.datetime):
+            completed_at = self.completed_at.isoformat()
+        else:
+            completed_at = self.completed_at
+
+        result: Union[None, Unset, str]
+        if isinstance(self.result, Unset):
+            result = UNSET
+        elif isinstance(self.result, TestResultEnum):
+            result = self.result.value
+        else:
+            result = self.result
+
+        result_score: Union[None, Unset, float]
+        if isinstance(self.result_score, Unset):
+            result_score = UNSET
+        else:
+            result_score = self.result_score
+
+        result_score_change: Union[None, Unset, float]
+        if isinstance(self.result_score_change, Unset):
+            result_score_change = UNSET
+        else:
+            result_score_change = self.result_score_change
+
+        links: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.links, Unset):
+            links = UNSET
+        elif isinstance(self.links, Links):
+            links = self.links.to_dict()
+        else:
+            links = self.links
+
+        conversation_scores: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.conversation_scores, Unset):
+            conversation_scores = UNSET
+        elif isinstance(self.conversation_scores, TestRunConversationScores):
+            conversation_scores = self.conversation_scores.to_dict()
+        else:
+            conversation_scores = self.conversation_scores
+
+        metric_scores: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.metric_scores, Unset):
+            metric_scores = UNSET
+        elif isinstance(self.metric_scores, TestRunResultsMetricScoresType0):
+            metric_scores = self.metric_scores.to_dict()
+        else:
+            metric_scores = self.metric_scores
+
+        module_scores: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.module_scores, Unset):
+            module_scores = UNSET
+        elif isinstance(self.module_scores, TestRunResultsModuleScoresType0):
+            module_scores = self.module_scores.to_dict()
+        else:
+            module_scores = self.module_scores
+
+        module_group_scores: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.module_group_scores, Unset):
+            module_group_scores = UNSET
+        elif isinstance(self.module_group_scores, TestRunResultsModuleGroupScoresType0):
+            module_group_scores = self.module_group_scores.to_dict()
+        else:
+            module_group_scores = self.module_group_scores
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "id": id,
+                "created_at": created_at,
+                "updated_at": updated_at,
+                "name": name,
+                "test_id": test_id,
+                "test_name": test_name,
+                "agent_target_id": agent_target_id,
+                "agent_target_name": agent_target_name,
+                "status": status,
+            }
+        )
+        if label is not UNSET:
+            field_dict["label"] = label
+        if test_label is not UNSET:
+            field_dict["test_label"] = test_label
+        if agent_target_label is not UNSET:
+            field_dict["agent_target_label"] = agent_target_label
+        if started_at is not UNSET:
+            field_dict["started_at"] = started_at
+        if completed_at is not UNSET:
+            field_dict["completed_at"] = completed_at
+        if result is not UNSET:
+            field_dict["result"] = result
+        if result_score is not UNSET:
+            field_dict["result_score"] = result_score
+        if result_score_change is not UNSET:
+            field_dict["result_score_change"] = result_score_change
+        if links is not UNSET:
+            field_dict["links"] = links
+        if conversation_scores is not UNSET:
+            field_dict["conversation_scores"] = conversation_scores
+        if metric_scores is not UNSET:
+            field_dict["metric_scores"] = metric_scores
+        if module_scores is not UNSET:
+            field_dict["module_scores"] = module_scores
+        if module_group_scores is not UNSET:
+            field_dict["module_group_scores"] = module_group_scores
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.links import Links
+        from ..models.test_run_conversation_scores import TestRunConversationScores
+        from ..models.test_run_results_metric_scores_type_0 import TestRunResultsMetricScoresType0
+        from ..models.test_run_results_module_group_scores_type_0 import TestRunResultsModuleGroupScoresType0
+        from ..models.test_run_results_module_scores_type_0 import TestRunResultsModuleScoresType0
+
+        d = src_dict.copy()
+        id = d.pop("id")
+
+        created_at = isoparse(d.pop("created_at"))
+
+        updated_at = isoparse(d.pop("updated_at"))
+
+        name = d.pop("name")
+
+        test_id = d.pop("test_id")
+
+        test_name = d.pop("test_name")
+
+        agent_target_id = d.pop("agent_target_id")
+
+        agent_target_name = d.pop("agent_target_name")
+
+        status = TestStatusEnum(d.pop("status"))
+
+        def _parse_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        label = _parse_label(d.pop("label", UNSET))
+
+        def _parse_test_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        test_label = _parse_test_label(d.pop("test_label", UNSET))
+
+        def _parse_agent_target_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_target_label = _parse_agent_target_label(d.pop("agent_target_label", UNSET))
+
+        def _parse_started_at(data: object) -> Union[None, Unset, datetime.datetime]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, str):
+                    raise TypeError()
+                started_at_type_0 = isoparse(data)
+
+                return started_at_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union[None, Unset, datetime.datetime], data)
+
+        started_at = _parse_started_at(d.pop("started_at", UNSET))
+
+        def _parse_completed_at(data: object) -> Union[None, Unset, datetime.datetime]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, str):
+                    raise TypeError()
+                completed_at_type_0 = isoparse(data)
+
+                return completed_at_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union[None, Unset, datetime.datetime], data)
+
+        completed_at = _parse_completed_at(d.pop("completed_at", UNSET))
+
+        def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, str):
+                    raise TypeError()
+                result_type_0 = TestResultEnum(data)
+
+                return result_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union[None, TestResultEnum, Unset], data)
+
+        result = _parse_result(d.pop("result", UNSET))
+
+        def _parse_result_score(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        result_score = _parse_result_score(d.pop("result_score", UNSET))
+
+        def _parse_result_score_change(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        result_score_change = _parse_result_score_change(d.pop("result_score_change", UNSET))
+
+        def _parse_links(data: object) -> Union["Links", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                links_type_0 = Links.from_dict(data)
+
+                return links_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["Links", None, Unset], data)
+
+        links = _parse_links(d.pop("links", UNSET))
+
+        def _parse_conversation_scores(data: object) -> Union["TestRunConversationScores", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                conversation_scores_type_0 = TestRunConversationScores.from_dict(data)
+
+                return conversation_scores_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunConversationScores", None, Unset], data)
+
+        conversation_scores = _parse_conversation_scores(d.pop("conversation_scores", UNSET))
+
+        def _parse_metric_scores(data: object) -> Union["TestRunResultsMetricScoresType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                metric_scores_type_0 = TestRunResultsMetricScoresType0.from_dict(data)
+
+                return metric_scores_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunResultsMetricScoresType0", None, Unset], data)
+
+        metric_scores = _parse_metric_scores(d.pop("metric_scores", UNSET))
+
+        def _parse_module_scores(data: object) -> Union["TestRunResultsModuleScoresType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                module_scores_type_0 = TestRunResultsModuleScoresType0.from_dict(data)
+
+                return module_scores_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunResultsModuleScoresType0", None, Unset], data)
+
+        module_scores = _parse_module_scores(d.pop("module_scores", UNSET))
+
+        def _parse_module_group_scores(data: object) -> Union["TestRunResultsModuleGroupScoresType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                module_group_scores_type_0 = TestRunResultsModuleGroupScoresType0.from_dict(data)
+
+                return module_group_scores_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunResultsModuleGroupScoresType0", None, Unset], data)
+
+        module_group_scores = _parse_module_group_scores(d.pop("module_group_scores", UNSET))
+
+        test_run_results = cls(
+            id=id,
+            created_at=created_at,
+            updated_at=updated_at,
+            name=name,
+            test_id=test_id,
+            test_name=test_name,
+            agent_target_id=agent_target_id,
+            agent_target_name=agent_target_name,
+            status=status,
+            label=label,
+            test_label=test_label,
+            agent_target_label=agent_target_label,
+            started_at=started_at,
+            completed_at=completed_at,
+            result=result,
+            result_score=result_score,
+            result_score_change=result_score_change,
+            links=links,
+            conversation_scores=conversation_scores,
+            metric_scores=metric_scores,
+            module_scores=module_scores,
+            module_group_scores=module_group_scores,
+        )
+
+        test_run_results.additional_properties = d
+        return test_run_results
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/test_run_results_conversations.py b/src/maihem/api_client/maihem_client/models/test_run_results_conversations.py
new file mode 100644
index 0000000..6f18b56
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/test_run_results_conversations.py
@@ -0,0 +1,529 @@
+import datetime
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar, Union, cast
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+from dateutil.parser import isoparse
+
+from ..models.test_result_enum import TestResultEnum
+from ..models.test_status_enum import TestStatusEnum
+from ..types import UNSET, Unset
+
+if TYPE_CHECKING:
+    from ..models.conversation_nested import ConversationNested
+    from ..models.links import Links
+    from ..models.test_run_conversation_scores import TestRunConversationScores
+    from ..models.test_run_results_conversations_metric_scores_type_0 import (
+        TestRunResultsConversationsMetricScoresType0,
+    )
+    from ..models.test_run_results_conversations_module_group_scores_type_0 import (
+        TestRunResultsConversationsModuleGroupScoresType0,
+    )
+    from ..models.test_run_results_conversations_module_scores_type_0 import (
+        TestRunResultsConversationsModuleScoresType0,
+    )
+
+
+T = TypeVar("T", bound="TestRunResultsConversations")
+
+
+@_attrs_define
+class TestRunResultsConversations:
+    """
+    Attributes:
+        id (str):
+        created_at (datetime.datetime):
+        updated_at (datetime.datetime):
+        name (str):
+        test_id (str):
+        test_name (str):
+        agent_target_id (str):
+        agent_target_name (str):
+        status (TestStatusEnum):
+        label (Union[None, Unset, str]):
+        test_label (Union[None, Unset, str]):
+        agent_target_label (Union[None, Unset, str]):
+        started_at (Union[None, Unset, datetime.datetime]):
+        completed_at (Union[None, Unset, datetime.datetime]):
+        result (Union[None, TestResultEnum, Unset]):
+        result_score (Union[None, Unset, float]):
+        result_score_change (Union[None, Unset, float]):
+        links (Union['Links', None, Unset]):
+        conversation_scores (Union['TestRunConversationScores', None, Unset]):
+        metric_scores (Union['TestRunResultsConversationsMetricScoresType0', None, Unset]):
+        module_scores (Union['TestRunResultsConversationsModuleScoresType0', None, Unset]):
+        module_group_scores (Union['TestRunResultsConversationsModuleGroupScoresType0', None, Unset]):
+        conversations (Union[Unset, List['ConversationNested']]):
+    """
+
+    id: str
+    created_at: datetime.datetime
+    updated_at: datetime.datetime
+    name: str
+    test_id: str
+    test_name: str
+    agent_target_id: str
+    agent_target_name: str
+    status: TestStatusEnum
+    label: Union[None, Unset, str] = UNSET
+    test_label: Union[None, Unset, str] = UNSET
+    agent_target_label: Union[None, Unset, str] = UNSET
+    started_at: Union[None, Unset, datetime.datetime] = UNSET
+    completed_at: Union[None, Unset, datetime.datetime] = UNSET
+    result: Union[None, TestResultEnum, Unset] = UNSET
+    result_score: Union[None, Unset, float] = UNSET
+    result_score_change: Union[None, Unset, float] = UNSET
+    links: Union["Links", None, Unset] = UNSET
+    conversation_scores: Union["TestRunConversationScores", None, Unset] = UNSET
+    metric_scores: Union["TestRunResultsConversationsMetricScoresType0", None, Unset] = UNSET
+    module_scores: Union["TestRunResultsConversationsModuleScoresType0", None, Unset] = UNSET
+    module_group_scores: Union["TestRunResultsConversationsModuleGroupScoresType0", None, Unset] = UNSET
+    conversations: Union[Unset, List["ConversationNested"]] = UNSET
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        from ..models.links import Links
+        from ..models.test_run_conversation_scores import TestRunConversationScores
+        from ..models.test_run_results_conversations_metric_scores_type_0 import (
+            TestRunResultsConversationsMetricScoresType0,
+        )
+        from ..models.test_run_results_conversations_module_group_scores_type_0 import (
+            TestRunResultsConversationsModuleGroupScoresType0,
+        )
+        from ..models.test_run_results_conversations_module_scores_type_0 import (
+            TestRunResultsConversationsModuleScoresType0,
+        )
+
+        id = self.id
+
+        created_at = self.created_at.isoformat()
+
+        updated_at = self.updated_at.isoformat()
+
+        name = self.name
+
+        test_id = self.test_id
+
+        test_name = self.test_name
+
+        agent_target_id = self.agent_target_id
+
+        agent_target_name = self.agent_target_name
+
+        status = self.status.value
+
+        label: Union[None, Unset, str]
+        if isinstance(self.label, Unset):
+            label = UNSET
+        else:
+            label = self.label
+
+        test_label: Union[None, Unset, str]
+        if isinstance(self.test_label, Unset):
+            test_label = UNSET
+        else:
+            test_label = self.test_label
+
+        agent_target_label: Union[None, Unset, str]
+        if isinstance(self.agent_target_label, Unset):
+            agent_target_label = UNSET
+        else:
+            agent_target_label = self.agent_target_label
+
+        started_at: Union[None, Unset, str]
+        if isinstance(self.started_at, Unset):
+            started_at = UNSET
+        elif isinstance(self.started_at, datetime.datetime):
+            started_at = self.started_at.isoformat()
+        else:
+            started_at = self.started_at
+
+        completed_at: Union[None, Unset, str]
+        if isinstance(self.completed_at, Unset):
+            completed_at = UNSET
+        elif isinstance(self.completed_at, datetime.datetime):
+            completed_at = self.completed_at.isoformat()
+        else:
+            completed_at = self.completed_at
+
+        result: Union[None, Unset, str]
+        if isinstance(self.result, Unset):
+            result = UNSET
+        elif isinstance(self.result, TestResultEnum):
+            result = self.result.value
+        else:
+            result = self.result
+
+        result_score: Union[None, Unset, float]
+        if isinstance(self.result_score, Unset):
+            result_score = UNSET
+        else:
+            result_score = self.result_score
+
+        result_score_change: Union[None, Unset, float]
+        if isinstance(self.result_score_change, Unset):
+            result_score_change = UNSET
+        else:
+            result_score_change = self.result_score_change
+
+        links: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.links, Unset):
+            links = UNSET
+        elif isinstance(self.links, Links):
+            links = self.links.to_dict()
+        else:
+            links = self.links
+
+        conversation_scores: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.conversation_scores, Unset):
+            conversation_scores = UNSET
+        elif isinstance(self.conversation_scores, TestRunConversationScores):
+            conversation_scores = self.conversation_scores.to_dict()
+        else:
+            conversation_scores = self.conversation_scores
+
+        metric_scores: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.metric_scores, Unset):
+            metric_scores = UNSET
+        elif isinstance(self.metric_scores, TestRunResultsConversationsMetricScoresType0):
+            metric_scores = self.metric_scores.to_dict()
+        else:
+            metric_scores = self.metric_scores
+
+        module_scores: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.module_scores, Unset):
+            module_scores = UNSET
+        elif isinstance(self.module_scores, TestRunResultsConversationsModuleScoresType0):
+            module_scores = self.module_scores.to_dict()
+        else:
+            module_scores = self.module_scores
+
+        module_group_scores: Union[Dict[str, Any], None, Unset]
+        if isinstance(self.module_group_scores, Unset):
+            module_group_scores = UNSET
+        elif isinstance(self.module_group_scores, TestRunResultsConversationsModuleGroupScoresType0):
+            module_group_scores = self.module_group_scores.to_dict()
+        else:
+            module_group_scores = self.module_group_scores
+
+        conversations: Union[Unset, List[Dict[str, Any]]] = UNSET
+        if not isinstance(self.conversations, Unset):
+            conversations = []
+            for conversations_item_data in self.conversations:
+                conversations_item = conversations_item_data.to_dict()
+                conversations.append(conversations_item)
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "id": id,
+                "created_at": created_at,
+                "updated_at": updated_at,
+                "name": name,
+                "test_id": test_id,
+                "test_name": test_name,
+                "agent_target_id": agent_target_id,
+                "agent_target_name": agent_target_name,
+                "status": status,
+            }
+        )
+        if label is not UNSET:
+            field_dict["label"] = label
+        if test_label is not UNSET:
+            field_dict["test_label"] = test_label
+        if agent_target_label is not UNSET:
+            field_dict["agent_target_label"] = agent_target_label
+        if started_at is not UNSET:
+            field_dict["started_at"] = started_at
+        if completed_at is not UNSET:
+            field_dict["completed_at"] = completed_at
+        if result is not UNSET:
+            field_dict["result"] = result
+        if result_score is not UNSET:
+            field_dict["result_score"] = result_score
+        if result_score_change is not UNSET:
+            field_dict["result_score_change"] = result_score_change
+        if links is not UNSET:
+            field_dict["links"] = links
+        if conversation_scores is not UNSET:
+            field_dict["conversation_scores"] = conversation_scores
+        if metric_scores is not UNSET:
+            field_dict["metric_scores"] = metric_scores
+        if module_scores is not UNSET:
+            field_dict["module_scores"] = module_scores
+        if module_group_scores is not UNSET:
+            field_dict["module_group_scores"] = module_group_scores
+        if conversations is not UNSET:
+            field_dict["conversations"] = conversations
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.conversation_nested import ConversationNested
+        from ..models.links import Links
+        from ..models.test_run_conversation_scores import TestRunConversationScores
+        from ..models.test_run_results_conversations_metric_scores_type_0 import (
+            TestRunResultsConversationsMetricScoresType0,
+        )
+        from ..models.test_run_results_conversations_module_group_scores_type_0 import (
+            TestRunResultsConversationsModuleGroupScoresType0,
+        )
+        from ..models.test_run_results_conversations_module_scores_type_0 import (
+            TestRunResultsConversationsModuleScoresType0,
+        )
+
+        d = src_dict.copy()
+        id = d.pop("id")
+
+        created_at = isoparse(d.pop("created_at"))
+
+        updated_at = isoparse(d.pop("updated_at"))
+
+        name = d.pop("name")
+
+        test_id = d.pop("test_id")
+
+        test_name = d.pop("test_name")
+
+        agent_target_id = d.pop("agent_target_id")
+
+        agent_target_name = d.pop("agent_target_name")
+
+        status = TestStatusEnum(d.pop("status"))
+
+        def _parse_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        label = _parse_label(d.pop("label", UNSET))
+
+        def _parse_test_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        test_label = _parse_test_label(d.pop("test_label", UNSET))
+
+        def _parse_agent_target_label(data: object) -> Union[None, Unset, str]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, str], data)
+
+        agent_target_label = _parse_agent_target_label(d.pop("agent_target_label", UNSET))
+
+        def _parse_started_at(data: object) -> Union[None, Unset, datetime.datetime]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, str):
+                    raise TypeError()
+                started_at_type_0 = isoparse(data)
+
+                return started_at_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union[None, Unset, datetime.datetime], data)
+
+        started_at = _parse_started_at(d.pop("started_at", UNSET))
+
+        def _parse_completed_at(data: object) -> Union[None, Unset, datetime.datetime]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, str):
+                    raise TypeError()
+                completed_at_type_0 = isoparse(data)
+
+                return completed_at_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union[None, Unset, datetime.datetime], data)
+
+        completed_at = _parse_completed_at(d.pop("completed_at", UNSET))
+
+        def _parse_result(data: object) -> Union[None, TestResultEnum, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, str):
+                    raise TypeError()
+                result_type_0 = TestResultEnum(data)
+
+                return result_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union[None, TestResultEnum, Unset], data)
+
+        result = _parse_result(d.pop("result", UNSET))
+
+        def _parse_result_score(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        result_score = _parse_result_score(d.pop("result_score", UNSET))
+
+        def _parse_result_score_change(data: object) -> Union[None, Unset, float]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            return cast(Union[None, Unset, float], data)
+
+        result_score_change = _parse_result_score_change(d.pop("result_score_change", UNSET))
+
+        def _parse_links(data: object) -> Union["Links", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                links_type_0 = Links.from_dict(data)
+
+                return links_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["Links", None, Unset], data)
+
+        links = _parse_links(d.pop("links", UNSET))
+
+        def _parse_conversation_scores(data: object) -> Union["TestRunConversationScores", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                conversation_scores_type_0 = TestRunConversationScores.from_dict(data)
+
+                return conversation_scores_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunConversationScores", None, Unset], data)
+
+        conversation_scores = _parse_conversation_scores(d.pop("conversation_scores", UNSET))
+
+        def _parse_metric_scores(data: object) -> Union["TestRunResultsConversationsMetricScoresType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                metric_scores_type_0 = TestRunResultsConversationsMetricScoresType0.from_dict(data)
+
+                return metric_scores_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunResultsConversationsMetricScoresType0", None, Unset], data)
+
+        metric_scores = _parse_metric_scores(d.pop("metric_scores", UNSET))
+
+        def _parse_module_scores(data: object) -> Union["TestRunResultsConversationsModuleScoresType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                module_scores_type_0 = TestRunResultsConversationsModuleScoresType0.from_dict(data)
+
+                return module_scores_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunResultsConversationsModuleScoresType0", None, Unset], data)
+
+        module_scores = _parse_module_scores(d.pop("module_scores", UNSET))
+
+        def _parse_module_group_scores(
+            data: object,
+        ) -> Union["TestRunResultsConversationsModuleGroupScoresType0", None, Unset]:
+            if data is None:
+                return data
+            if isinstance(data, Unset):
+                return data
+            try:
+                if not isinstance(data, dict):
+                    raise TypeError()
+                module_group_scores_type_0 = TestRunResultsConversationsModuleGroupScoresType0.from_dict(data)
+
+                return module_group_scores_type_0
+            except:  # noqa: E722
+                pass
+            return cast(Union["TestRunResultsConversationsModuleGroupScoresType0", None, Unset], data)
+
+        module_group_scores = _parse_module_group_scores(d.pop("module_group_scores", UNSET))
+
+        conversations = []
+        _conversations = d.pop("conversations", UNSET)
+        for conversations_item_data in _conversations or []:
+            conversations_item = ConversationNested.from_dict(conversations_item_data)
+
+            conversations.append(conversations_item)
+
+        test_run_results_conversations = cls(
+            id=id,
+            created_at=created_at,
+            updated_at=updated_at,
+            name=name,
+            test_id=test_id,
+            test_name=test_name,
+            agent_target_id=agent_target_id,
+            agent_target_name=agent_target_name,
+            status=status,
+            label=label,
+            test_label=test_label,
+            agent_target_label=agent_target_label,
+            started_at=started_at,
+            completed_at=completed_at,
+            result=result,
+            result_score=result_score,
+            result_score_change=result_score_change,
+            links=links,
+            conversation_scores=conversation_scores,
+            metric_scores=metric_scores,
+            module_scores=module_scores,
+            module_group_scores=module_group_scores,
+            conversations=conversations,
+        )
+
+        test_run_results_conversations.additional_properties = d
+        return test_run_results_conversations
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations_metric_scores_type_0.py b/src/maihem/api_client/maihem_client/models/test_run_results_conversations_metric_scores_type_0.py
similarity index 52%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations_metric_scores_type_0.py
rename to src/maihem/api_client/maihem_client/models/test_run_results_conversations_metric_scores_type_0.py
index c86e269..3e57b97 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_result_conversations_metric_scores_type_0.py
+++ b/src/maihem/api_client/maihem_client/models/test_run_results_conversations_metric_scores_type_0.py
@@ -4,17 +4,17 @@
 from attrs import field as _attrs_field
 
 if TYPE_CHECKING:
-    from ..models.api_schema_test_run_result_metric_scores import APISchemaTestRunResultMetricScores
+    from ..models.test_run_metric_scores import TestRunMetricScores
 
 
-T = TypeVar("T", bound="APISchemaTestRunResultConversationsMetricScoresType0")
+T = TypeVar("T", bound="TestRunResultsConversationsMetricScoresType0")
 
 
 @_attrs_define
-class APISchemaTestRunResultConversationsMetricScoresType0:
+class TestRunResultsConversationsMetricScoresType0:
     """ """
 
-    additional_properties: Dict[str, "APISchemaTestRunResultMetricScores"] = _attrs_field(init=False, factory=dict)
+    additional_properties: Dict[str, "TestRunMetricScores"] = _attrs_field(init=False, factory=dict)
 
     def to_dict(self) -> Dict[str, Any]:
         field_dict: Dict[str, Any] = {}
@@ -25,28 +25,28 @@ def to_dict(self) -> Dict[str, Any]:
 
     @classmethod
     def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
-        from ..models.api_schema_test_run_result_metric_scores import APISchemaTestRunResultMetricScores
+        from ..models.test_run_metric_scores import TestRunMetricScores
 
         d = src_dict.copy()
-        api_schema_test_run_result_conversations_metric_scores_type_0 = cls()
+        test_run_results_conversations_metric_scores_type_0 = cls()
 
         additional_properties = {}
         for prop_name, prop_dict in d.items():
-            additional_property = APISchemaTestRunResultMetricScores.from_dict(prop_dict)
+            additional_property = TestRunMetricScores.from_dict(prop_dict)
 
             additional_properties[prop_name] = additional_property
 
-        api_schema_test_run_result_conversations_metric_scores_type_0.additional_properties = additional_properties
-        return api_schema_test_run_result_conversations_metric_scores_type_0
+        test_run_results_conversations_metric_scores_type_0.additional_properties = additional_properties
+        return test_run_results_conversations_metric_scores_type_0
 
     @property
     def additional_keys(self) -> List[str]:
         return list(self.additional_properties.keys())
 
-    def __getitem__(self, key: str) -> "APISchemaTestRunResultMetricScores":
+    def __getitem__(self, key: str) -> "TestRunMetricScores":
         return self.additional_properties[key]
 
-    def __setitem__(self, key: str, value: "APISchemaTestRunResultMetricScores") -> None:
+    def __setitem__(self, key: str, value: "TestRunMetricScores") -> None:
         self.additional_properties[key] = value
 
     def __delitem__(self, key: str) -> None:
diff --git a/src/maihem/api_client/maihem_client/models/test_run_results_conversations_module_group_scores_type_0.py b/src/maihem/api_client/maihem_client/models/test_run_results_conversations_module_group_scores_type_0.py
new file mode 100644
index 0000000..ff75933
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/test_run_results_conversations_module_group_scores_type_0.py
@@ -0,0 +1,56 @@
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+if TYPE_CHECKING:
+    from ..models.test_run_metric_scores import TestRunMetricScores
+
+
+T = TypeVar("T", bound="TestRunResultsConversationsModuleGroupScoresType0")
+
+
+@_attrs_define
+class TestRunResultsConversationsModuleGroupScoresType0:
+    """ """
+
+    additional_properties: Dict[str, "TestRunMetricScores"] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        field_dict: Dict[str, Any] = {}
+        for prop_name, prop in self.additional_properties.items():
+            field_dict[prop_name] = prop.to_dict()
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.test_run_metric_scores import TestRunMetricScores
+
+        d = src_dict.copy()
+        test_run_results_conversations_module_group_scores_type_0 = cls()
+
+        additional_properties = {}
+        for prop_name, prop_dict in d.items():
+            additional_property = TestRunMetricScores.from_dict(prop_dict)
+
+            additional_properties[prop_name] = additional_property
+
+        test_run_results_conversations_module_group_scores_type_0.additional_properties = additional_properties
+        return test_run_results_conversations_module_group_scores_type_0
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> "TestRunMetricScores":
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: "TestRunMetricScores") -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/test_run_results_conversations_module_scores_type_0.py b/src/maihem/api_client/maihem_client/models/test_run_results_conversations_module_scores_type_0.py
new file mode 100644
index 0000000..11a1002
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/test_run_results_conversations_module_scores_type_0.py
@@ -0,0 +1,56 @@
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+if TYPE_CHECKING:
+    from ..models.test_run_metric_scores import TestRunMetricScores
+
+
+T = TypeVar("T", bound="TestRunResultsConversationsModuleScoresType0")
+
+
+@_attrs_define
+class TestRunResultsConversationsModuleScoresType0:
+    """ """
+
+    additional_properties: Dict[str, "TestRunMetricScores"] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        field_dict: Dict[str, Any] = {}
+        for prop_name, prop in self.additional_properties.items():
+            field_dict[prop_name] = prop.to_dict()
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.test_run_metric_scores import TestRunMetricScores
+
+        d = src_dict.copy()
+        test_run_results_conversations_module_scores_type_0 = cls()
+
+        additional_properties = {}
+        for prop_name, prop_dict in d.items():
+            additional_property = TestRunMetricScores.from_dict(prop_dict)
+
+            additional_properties[prop_name] = additional_property
+
+        test_run_results_conversations_module_scores_type_0.additional_properties = additional_properties
+        return test_run_results_conversations_module_scores_type_0
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> "TestRunMetricScores":
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: "TestRunMetricScores") -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/test_run_results_metric_scores_type_0.py b/src/maihem/api_client/maihem_client/models/test_run_results_metric_scores_type_0.py
new file mode 100644
index 0000000..cc35801
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/test_run_results_metric_scores_type_0.py
@@ -0,0 +1,56 @@
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+if TYPE_CHECKING:
+    from ..models.test_run_metric_scores import TestRunMetricScores
+
+
+T = TypeVar("T", bound="TestRunResultsMetricScoresType0")
+
+
+@_attrs_define
+class TestRunResultsMetricScoresType0:
+    """ """
+
+    additional_properties: Dict[str, "TestRunMetricScores"] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        field_dict: Dict[str, Any] = {}
+        for prop_name, prop in self.additional_properties.items():
+            field_dict[prop_name] = prop.to_dict()
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.test_run_metric_scores import TestRunMetricScores
+
+        d = src_dict.copy()
+        test_run_results_metric_scores_type_0 = cls()
+
+        additional_properties = {}
+        for prop_name, prop_dict in d.items():
+            additional_property = TestRunMetricScores.from_dict(prop_dict)
+
+            additional_properties[prop_name] = additional_property
+
+        test_run_results_metric_scores_type_0.additional_properties = additional_properties
+        return test_run_results_metric_scores_type_0
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> "TestRunMetricScores":
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: "TestRunMetricScores") -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/test_run_results_module_group_scores_type_0.py b/src/maihem/api_client/maihem_client/models/test_run_results_module_group_scores_type_0.py
new file mode 100644
index 0000000..8199937
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/test_run_results_module_group_scores_type_0.py
@@ -0,0 +1,56 @@
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+if TYPE_CHECKING:
+    from ..models.test_run_metric_scores import TestRunMetricScores
+
+
+T = TypeVar("T", bound="TestRunResultsModuleGroupScoresType0")
+
+
+@_attrs_define
+class TestRunResultsModuleGroupScoresType0:
+    """ """
+
+    additional_properties: Dict[str, "TestRunMetricScores"] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        field_dict: Dict[str, Any] = {}
+        for prop_name, prop in self.additional_properties.items():
+            field_dict[prop_name] = prop.to_dict()
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.test_run_metric_scores import TestRunMetricScores
+
+        d = src_dict.copy()
+        test_run_results_module_group_scores_type_0 = cls()
+
+        additional_properties = {}
+        for prop_name, prop_dict in d.items():
+            additional_property = TestRunMetricScores.from_dict(prop_dict)
+
+            additional_properties[prop_name] = additional_property
+
+        test_run_results_module_group_scores_type_0.additional_properties = additional_properties
+        return test_run_results_module_group_scores_type_0
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> "TestRunMetricScores":
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: "TestRunMetricScores") -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/test_run_results_module_scores_type_0.py b/src/maihem/api_client/maihem_client/models/test_run_results_module_scores_type_0.py
new file mode 100644
index 0000000..cfde5c4
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/test_run_results_module_scores_type_0.py
@@ -0,0 +1,56 @@
+from typing import TYPE_CHECKING, Any, Dict, List, Type, TypeVar
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+
+if TYPE_CHECKING:
+    from ..models.test_run_metric_scores import TestRunMetricScores
+
+
+T = TypeVar("T", bound="TestRunResultsModuleScoresType0")
+
+
+@_attrs_define
+class TestRunResultsModuleScoresType0:
+    """ """
+
+    additional_properties: Dict[str, "TestRunMetricScores"] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        field_dict: Dict[str, Any] = {}
+        for prop_name, prop in self.additional_properties.items():
+            field_dict[prop_name] = prop.to_dict()
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        from ..models.test_run_metric_scores import TestRunMetricScores
+
+        d = src_dict.copy()
+        test_run_results_module_scores_type_0 = cls()
+
+        additional_properties = {}
+        for prop_name, prop_dict in d.items():
+            additional_property = TestRunMetricScores.from_dict(prop_dict)
+
+            additional_properties[prop_name] = additional_property
+
+        test_run_results_module_scores_type_0.additional_properties = additional_properties
+        return test_run_results_module_scores_type_0
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> "TestRunMetricScores":
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: "TestRunMetricScores") -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/api_schema_test_run_status_update_request.py b/src/maihem/api_client/maihem_client/models/test_run_status_update_request.py
similarity index 82%
rename from src/maihem/api_client/maihem_client/models/api_schema_test_run_status_update_request.py
rename to src/maihem/api_client/maihem_client/models/test_run_status_update_request.py
index 9441dff..90a748a 100644
--- a/src/maihem/api_client/maihem_client/models/api_schema_test_run_status_update_request.py
+++ b/src/maihem/api_client/maihem_client/models/test_run_status_update_request.py
@@ -5,11 +5,11 @@
 
 from ..models.test_status_enum import TestStatusEnum
 
-T = TypeVar("T", bound="APISchemaTestRunStatusUpdateRequest")
+T = TypeVar("T", bound="TestRunStatusUpdateRequest")
 
 
 @_attrs_define
-class APISchemaTestRunStatusUpdateRequest:
+class TestRunStatusUpdateRequest:
     """
     Attributes:
         status (TestStatusEnum):
@@ -36,12 +36,12 @@ def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
         d = src_dict.copy()
         status = TestStatusEnum(d.pop("status"))
 
-        api_schema_test_run_status_update_request = cls(
+        test_run_status_update_request = cls(
             status=status,
         )
 
-        api_schema_test_run_status_update_request.additional_properties = d
-        return api_schema_test_run_status_update_request
+        test_run_status_update_request.additional_properties = d
+        return test_run_status_update_request
 
     @property
     def additional_keys(self) -> List[str]:
diff --git a/src/maihem/api_client/maihem_client/models/v_test_result_metric_review_audit.py b/src/maihem/api_client/maihem_client/models/v_test_result_metric_review_audit.py
new file mode 100644
index 0000000..505a48a
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/v_test_result_metric_review_audit.py
@@ -0,0 +1,200 @@
+import datetime
+from typing import Any, Dict, List, Type, TypeVar, Union, cast
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+from dateutil.parser import isoparse
+
+T = TypeVar("T", bound="VTestResultMetricReviewAudit")
+
+
+@_attrs_define
+class VTestResultMetricReviewAudit:
+    """
+    Attributes:
+        id (str):
+        created_at (datetime.datetime):
+        updated_at (datetime.datetime):
+        test_result_metric_id (str):
+        action (str):
+        event (str):
+        actioned_by (str):
+        actioned_at (datetime.datetime):
+        content (Union[None, str]):
+        trm_entity_type (str):
+        trm_entity_id (str):
+        actioned_by_first_name (str):
+        actioned_by_last_name (str):
+        actioned_by_image_url (Union[None, str]):
+        org_id (str):
+        test_run_id (str):
+        metric_id (str):
+    """
+
+    id: str
+    created_at: datetime.datetime
+    updated_at: datetime.datetime
+    test_result_metric_id: str
+    action: str
+    event: str
+    actioned_by: str
+    actioned_at: datetime.datetime
+    content: Union[None, str]
+    trm_entity_type: str
+    trm_entity_id: str
+    actioned_by_first_name: str
+    actioned_by_last_name: str
+    actioned_by_image_url: Union[None, str]
+    org_id: str
+    test_run_id: str
+    metric_id: str
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        id = self.id
+
+        created_at = self.created_at.isoformat()
+
+        updated_at = self.updated_at.isoformat()
+
+        test_result_metric_id = self.test_result_metric_id
+
+        action = self.action
+
+        event = self.event
+
+        actioned_by = self.actioned_by
+
+        actioned_at = self.actioned_at.isoformat()
+
+        content: Union[None, str]
+        content = self.content
+
+        trm_entity_type = self.trm_entity_type
+
+        trm_entity_id = self.trm_entity_id
+
+        actioned_by_first_name = self.actioned_by_first_name
+
+        actioned_by_last_name = self.actioned_by_last_name
+
+        actioned_by_image_url: Union[None, str]
+        actioned_by_image_url = self.actioned_by_image_url
+
+        org_id = self.org_id
+
+        test_run_id = self.test_run_id
+
+        metric_id = self.metric_id
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "id": id,
+                "created_at": created_at,
+                "updated_at": updated_at,
+                "test_result_metric_id": test_result_metric_id,
+                "action": action,
+                "event": event,
+                "actioned_by": actioned_by,
+                "actioned_at": actioned_at,
+                "content": content,
+                "trm_entity_type": trm_entity_type,
+                "trm_entity_id": trm_entity_id,
+                "actioned_by_first_name": actioned_by_first_name,
+                "actioned_by_last_name": actioned_by_last_name,
+                "actioned_by_image_url": actioned_by_image_url,
+                "org_id": org_id,
+                "test_run_id": test_run_id,
+                "metric_id": metric_id,
+            }
+        )
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        d = src_dict.copy()
+        id = d.pop("id")
+
+        created_at = isoparse(d.pop("created_at"))
+
+        updated_at = isoparse(d.pop("updated_at"))
+
+        test_result_metric_id = d.pop("test_result_metric_id")
+
+        action = d.pop("action")
+
+        event = d.pop("event")
+
+        actioned_by = d.pop("actioned_by")
+
+        actioned_at = isoparse(d.pop("actioned_at"))
+
+        def _parse_content(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        content = _parse_content(d.pop("content"))
+
+        trm_entity_type = d.pop("trm_entity_type")
+
+        trm_entity_id = d.pop("trm_entity_id")
+
+        actioned_by_first_name = d.pop("actioned_by_first_name")
+
+        actioned_by_last_name = d.pop("actioned_by_last_name")
+
+        def _parse_actioned_by_image_url(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        actioned_by_image_url = _parse_actioned_by_image_url(d.pop("actioned_by_image_url"))
+
+        org_id = d.pop("org_id")
+
+        test_run_id = d.pop("test_run_id")
+
+        metric_id = d.pop("metric_id")
+
+        v_test_result_metric_review_audit = cls(
+            id=id,
+            created_at=created_at,
+            updated_at=updated_at,
+            test_result_metric_id=test_result_metric_id,
+            action=action,
+            event=event,
+            actioned_by=actioned_by,
+            actioned_at=actioned_at,
+            content=content,
+            trm_entity_type=trm_entity_type,
+            trm_entity_id=trm_entity_id,
+            actioned_by_first_name=actioned_by_first_name,
+            actioned_by_last_name=actioned_by_last_name,
+            actioned_by_image_url=actioned_by_image_url,
+            org_id=org_id,
+            test_run_id=test_run_id,
+            metric_id=metric_id,
+        )
+
+        v_test_result_metric_review_audit.additional_properties = d
+        return v_test_result_metric_review_audit
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/api_client/maihem_client/models/v_test_result_metric_review_state.py b/src/maihem/api_client/maihem_client/models/v_test_result_metric_review_state.py
new file mode 100644
index 0000000..d4573a1
--- /dev/null
+++ b/src/maihem/api_client/maihem_client/models/v_test_result_metric_review_state.py
@@ -0,0 +1,274 @@
+import datetime
+from typing import Any, Dict, List, Type, TypeVar, Union, cast
+
+from attrs import define as _attrs_define
+from attrs import field as _attrs_field
+from dateutil.parser import isoparse
+
+T = TypeVar("T", bound="VTestResultMetricReviewState")
+
+
+@_attrs_define
+class VTestResultMetricReviewState:
+    """
+    Attributes:
+        id (str):
+        created_at (datetime.datetime):
+        updated_at (datetime.datetime):
+        test_result_metric_id (str):
+        is_result_reviewed (bool):
+        is_flagged_internal (bool):
+        is_flagged_customer (bool):
+        result_reviewed_by (Union[None, str]):
+        flagged_internal_by (Union[None, str]):
+        flagged_customer_by (Union[None, str]):
+        trm_entity_type (str):
+        trm_entity_id (str):
+        result_reviewed_by_first_name (Union[None, str]):
+        result_reviewed_by_last_name (Union[None, str]):
+        flagged_internal_by_first_name (Union[None, str]):
+        flagged_internal_by_last_name (Union[None, str]):
+        flagged_customer_by_first_name (Union[None, str]):
+        flagged_customer_by_last_name (Union[None, str]):
+        org_id (str):
+        test_run_id (str):
+        metric_id (str):
+    """
+
+    id: str
+    created_at: datetime.datetime
+    updated_at: datetime.datetime
+    test_result_metric_id: str
+    is_result_reviewed: bool
+    is_flagged_internal: bool
+    is_flagged_customer: bool
+    result_reviewed_by: Union[None, str]
+    flagged_internal_by: Union[None, str]
+    flagged_customer_by: Union[None, str]
+    trm_entity_type: str
+    trm_entity_id: str
+    result_reviewed_by_first_name: Union[None, str]
+    result_reviewed_by_last_name: Union[None, str]
+    flagged_internal_by_first_name: Union[None, str]
+    flagged_internal_by_last_name: Union[None, str]
+    flagged_customer_by_first_name: Union[None, str]
+    flagged_customer_by_last_name: Union[None, str]
+    org_id: str
+    test_run_id: str
+    metric_id: str
+    additional_properties: Dict[str, Any] = _attrs_field(init=False, factory=dict)
+
+    def to_dict(self) -> Dict[str, Any]:
+        id = self.id
+
+        created_at = self.created_at.isoformat()
+
+        updated_at = self.updated_at.isoformat()
+
+        test_result_metric_id = self.test_result_metric_id
+
+        is_result_reviewed = self.is_result_reviewed
+
+        is_flagged_internal = self.is_flagged_internal
+
+        is_flagged_customer = self.is_flagged_customer
+
+        result_reviewed_by: Union[None, str]
+        result_reviewed_by = self.result_reviewed_by
+
+        flagged_internal_by: Union[None, str]
+        flagged_internal_by = self.flagged_internal_by
+
+        flagged_customer_by: Union[None, str]
+        flagged_customer_by = self.flagged_customer_by
+
+        trm_entity_type = self.trm_entity_type
+
+        trm_entity_id = self.trm_entity_id
+
+        result_reviewed_by_first_name: Union[None, str]
+        result_reviewed_by_first_name = self.result_reviewed_by_first_name
+
+        result_reviewed_by_last_name: Union[None, str]
+        result_reviewed_by_last_name = self.result_reviewed_by_last_name
+
+        flagged_internal_by_first_name: Union[None, str]
+        flagged_internal_by_first_name = self.flagged_internal_by_first_name
+
+        flagged_internal_by_last_name: Union[None, str]
+        flagged_internal_by_last_name = self.flagged_internal_by_last_name
+
+        flagged_customer_by_first_name: Union[None, str]
+        flagged_customer_by_first_name = self.flagged_customer_by_first_name
+
+        flagged_customer_by_last_name: Union[None, str]
+        flagged_customer_by_last_name = self.flagged_customer_by_last_name
+
+        org_id = self.org_id
+
+        test_run_id = self.test_run_id
+
+        metric_id = self.metric_id
+
+        field_dict: Dict[str, Any] = {}
+        field_dict.update(self.additional_properties)
+        field_dict.update(
+            {
+                "id": id,
+                "created_at": created_at,
+                "updated_at": updated_at,
+                "test_result_metric_id": test_result_metric_id,
+                "is_result_reviewed": is_result_reviewed,
+                "is_flagged_internal": is_flagged_internal,
+                "is_flagged_customer": is_flagged_customer,
+                "result_reviewed_by": result_reviewed_by,
+                "flagged_internal_by": flagged_internal_by,
+                "flagged_customer_by": flagged_customer_by,
+                "trm_entity_type": trm_entity_type,
+                "trm_entity_id": trm_entity_id,
+                "result_reviewed_by_first_name": result_reviewed_by_first_name,
+                "result_reviewed_by_last_name": result_reviewed_by_last_name,
+                "flagged_internal_by_first_name": flagged_internal_by_first_name,
+                "flagged_internal_by_last_name": flagged_internal_by_last_name,
+                "flagged_customer_by_first_name": flagged_customer_by_first_name,
+                "flagged_customer_by_last_name": flagged_customer_by_last_name,
+                "org_id": org_id,
+                "test_run_id": test_run_id,
+                "metric_id": metric_id,
+            }
+        )
+
+        return field_dict
+
+    @classmethod
+    def from_dict(cls: Type[T], src_dict: Dict[str, Any]) -> T:
+        d = src_dict.copy()
+        id = d.pop("id")
+
+        created_at = isoparse(d.pop("created_at"))
+
+        updated_at = isoparse(d.pop("updated_at"))
+
+        test_result_metric_id = d.pop("test_result_metric_id")
+
+        is_result_reviewed = d.pop("is_result_reviewed")
+
+        is_flagged_internal = d.pop("is_flagged_internal")
+
+        is_flagged_customer = d.pop("is_flagged_customer")
+
+        def _parse_result_reviewed_by(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        result_reviewed_by = _parse_result_reviewed_by(d.pop("result_reviewed_by"))
+
+        def _parse_flagged_internal_by(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        flagged_internal_by = _parse_flagged_internal_by(d.pop("flagged_internal_by"))
+
+        def _parse_flagged_customer_by(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        flagged_customer_by = _parse_flagged_customer_by(d.pop("flagged_customer_by"))
+
+        trm_entity_type = d.pop("trm_entity_type")
+
+        trm_entity_id = d.pop("trm_entity_id")
+
+        def _parse_result_reviewed_by_first_name(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        result_reviewed_by_first_name = _parse_result_reviewed_by_first_name(d.pop("result_reviewed_by_first_name"))
+
+        def _parse_result_reviewed_by_last_name(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        result_reviewed_by_last_name = _parse_result_reviewed_by_last_name(d.pop("result_reviewed_by_last_name"))
+
+        def _parse_flagged_internal_by_first_name(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        flagged_internal_by_first_name = _parse_flagged_internal_by_first_name(d.pop("flagged_internal_by_first_name"))
+
+        def _parse_flagged_internal_by_last_name(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        flagged_internal_by_last_name = _parse_flagged_internal_by_last_name(d.pop("flagged_internal_by_last_name"))
+
+        def _parse_flagged_customer_by_first_name(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        flagged_customer_by_first_name = _parse_flagged_customer_by_first_name(d.pop("flagged_customer_by_first_name"))
+
+        def _parse_flagged_customer_by_last_name(data: object) -> Union[None, str]:
+            if data is None:
+                return data
+            return cast(Union[None, str], data)
+
+        flagged_customer_by_last_name = _parse_flagged_customer_by_last_name(d.pop("flagged_customer_by_last_name"))
+
+        org_id = d.pop("org_id")
+
+        test_run_id = d.pop("test_run_id")
+
+        metric_id = d.pop("metric_id")
+
+        v_test_result_metric_review_state = cls(
+            id=id,
+            created_at=created_at,
+            updated_at=updated_at,
+            test_result_metric_id=test_result_metric_id,
+            is_result_reviewed=is_result_reviewed,
+            is_flagged_internal=is_flagged_internal,
+            is_flagged_customer=is_flagged_customer,
+            result_reviewed_by=result_reviewed_by,
+            flagged_internal_by=flagged_internal_by,
+            flagged_customer_by=flagged_customer_by,
+            trm_entity_type=trm_entity_type,
+            trm_entity_id=trm_entity_id,
+            result_reviewed_by_first_name=result_reviewed_by_first_name,
+            result_reviewed_by_last_name=result_reviewed_by_last_name,
+            flagged_internal_by_first_name=flagged_internal_by_first_name,
+            flagged_internal_by_last_name=flagged_internal_by_last_name,
+            flagged_customer_by_first_name=flagged_customer_by_first_name,
+            flagged_customer_by_last_name=flagged_customer_by_last_name,
+            org_id=org_id,
+            test_run_id=test_run_id,
+            metric_id=metric_id,
+        )
+
+        v_test_result_metric_review_state.additional_properties = d
+        return v_test_result_metric_review_state
+
+    @property
+    def additional_keys(self) -> List[str]:
+        return list(self.additional_properties.keys())
+
+    def __getitem__(self, key: str) -> Any:
+        return self.additional_properties[key]
+
+    def __setitem__(self, key: str, value: Any) -> None:
+        self.additional_properties[key] = value
+
+    def __delitem__(self, key: str) -> None:
+        del self.additional_properties[key]
+
+    def __contains__(self, key: str) -> bool:
+        return key in self.additional_properties
diff --git a/src/maihem/schemas/tests.py b/src/maihem/schemas/tests.py
index 7859a70..0f457ad 100644
--- a/src/maihem/schemas/tests.py
+++ b/src/maihem/schemas/tests.py
@@ -36,12 +36,14 @@ class Test(BaseModel):
     id: str
     created_at: datetime
     updated_at: datetime
-    identifier: str
+    name: str
     agent_target_id: str
-    name: Optional[str] = None
+    label: Optional[str] = None
     initiating_agent: AgentType = AgentType.MAIHEM
     conversation_turns_max: Optional[int] = None
     agent_maihem_behavior_prompt: Optional[str] = None
+    agent_maihem_goal_prompt: Optional[str] = None
+    agent_maihem_population_prompt: Optional[str] = None
     metrics_config: Dict[str, int] = {}
 
 
@@ -117,33 +119,116 @@ class Config:
         arbitrary_types_allowed = True
 
 
-class SimulatedConversation:
-    """
-    Class with the response messages and evaluation from a simulated conversation
+class ResultEvaluation(BaseModel):
+    criteria: str
+    is_failure: bool
+    explanation: Optional[str] = None
 
-    messages: List[Dict[str, str]] - List of messages from the conversation
-    evaluation: str - Explanation of the evaluation of the conversation
-    """
+    def __str__(self):
+        return json.dumps(self.model_dump(), default=str, indent=4)
 
-    def __init__(self, conversation: TestRunResultConversations, conv_num: int = 0):
-        self.conv_num = conv_num
-        try:
-            self.messages = self._convert_conv_to_message_list(conversation)
-        except Exception as e:
-            self.messages = None
-        try:
-            self.evaluation = (
-                conversation.conversations[conv_num].evaluations[0].explanation
-            )
-        except Exception as e:
-            self.evaluation = None
 
-    def _convert_conv_to_message_list(self, conversation: TestRunResultConversations):
-        conv = conversation.conversations[self.conv_num]
-        message_list = []
+class ResultConversationMessage(BaseModel):
+    role: str
+    content: str
+    failed_evaluations: Optional[List[ResultEvaluation]] = None
 
-        for turn in conv.conversation_turns:
-            for message in turn.conversation_messages:
-                message_list.append({message.agent_type.value: message.content})
+    def __str__(self):
+        return json.dumps(self.model_dump(), default=str, indent=4)
 
-        return message_list
+
+class ResultConversation(BaseModel):
+    messages: List[ResultConversationMessage]
+    failed_evaluations: Optional[List[ResultEvaluation]] = None
+
+    def __str__(self):
+        return json.dumps(self.model_dump(), default=str, indent=4)
+
+
+class ResultTestRun(BaseModel):
+    result: Optional[TestResultEnum] = None
+    score: Optional[float] = None
+    conversations: Optional[List[ResultConversation]] = None
+    id: Optional[str] = None
+
+    def __str__(self):
+        return json.dumps(self.model_dump(), default=str, indent=4)
+
+    def __init__(self, test_run_api: TestRunResultConversations):
+        super().__init__()
+
+        conversations = []
+        for conv in test_run_api.conversations:
+            messages = []
+            for turn in conv.conversation_turns:
+                for msg in turn.conversation_messages:
+                    evaluations_msg = []
+                    for evl in msg.evaluations:
+                        is_failure = evl.result.value == "failed"
+                        if is_failure:
+                            evaluation_msg = ResultEvaluation(
+                                criteria=evl.criteria,
+                                is_failure=is_failure,
+                                explanation=evl.explanation,
+                            )
+                            evaluations_msg.append(evaluation_msg)
+
+                    message = ResultConversationMessage(
+                        role=msg.agent_type.value,
+                        content=msg.content,
+                        failed_evaluations=evaluations_msg,
+                    )
+                    messages.append(message)
+
+            evaluations = []
+            for evl in conv.evaluations:
+                is_failure = evl.result.value == "failed"
+                if is_failure:
+                    evaluation = ResultEvaluation(
+                        criteria=evl.criteria,
+                        is_failure=is_failure,
+                        explanation=evl.explanation,
+                    )
+                    evaluations.append(evaluation)
+
+            conversation = ResultConversation(
+                messages=messages, failed_evaluations=evaluations
+            )
+            conversations.append(conversation)
+
+        self.id = test_run_api.id
+        self.result = test_run_api.result
+        self.score = test_run_api.result_score
+        self.conversations = conversations
+
+
+# class SimulatedConversation:
+#     """
+#     Class with the response messages and evaluation from a simulated conversation
+
+#     messages: List[Dict[str, str]] - List of messages from the conversation
+#     evaluation: str - Explanation of the evaluation of the conversation
+#     """
+
+#     def __init__(self, conversation: TestRunResultConversations, conv_num: int = 0):
+#         self.conv_num = conv_num
+#         try:
+#             self.messages = self._convert_conv_to_message_list(conversation)
+#         except Exception as e:
+#             self.messages = None
+#         try:
+#             self.evaluation = (
+#                 conversation.conversations[conv_num].evaluations[0].explanation
+#             )
+#         except Exception as e:
+#             self.evaluation = None
+
+#     def _convert_conv_to_message_list(self, conversation: TestRunResultConversations):
+#         conv = conversation.conversations[self.conv_num]
+#         message_list = []
+
+#         for turn in conv.conversation_turns:
+#             for message in turn.conversation_messages:
+#                 message_list.append({message.agent_type.value: message.content})
+
+#         return message_list
diff --git a/src/maihem_config_test_mode.yaml b/src/maihem_config_test_mode.yaml
deleted file mode 100644
index d580292..0000000
--- a/src/maihem_config_test_mode.yaml
+++ /dev/null
@@ -1,24 +0,0 @@
-target_agent:
-  tg_ag_therapy_1: # Unique identifier for the target agent.
-    name: Acme Therapy Agent
-    role: mental health assistant
-    industry: mental health
-    description: A chatbot for emotional support through Cognitive Behavioral Therapy (CBT)
-    language: en  
-test:
-  test_a: # Unique identifier for the test
-    name: Test venting (Model A)
-    metrics: # See list of supported metrics here: https://docs.maihem.ai/metrics/collection
-      - qa_cx_helpfulness
-      - qa_cx_goal_completion
-      - qa_cx_retention
-      - qa_rag_hallucination
-      - qa_rag_answer_relevance
-      - sec_brand_competitor_recommendation
-      - sec_bias_gender
-    behavior_prompt: Vent about your problems this week
-    initiating_agent: maihem
-    conversation_turns_max: 5
-    # documents: # (Optional) Load documents for RAG question generation
-    #   - /path_to_doc_1.pdf
-    #   - /path_to_doc_2.txt
\ No newline at end of file
diff --git a/test_api_client.py b/test_api_client.py
deleted file mode 100644
index 986d5cd..0000000
--- a/test_api_client.py
+++ /dev/null
@@ -1,81 +0,0 @@
-import sys
-import os
-import requests
-import time
-import json
-from tqdm import tqdm
-
-sys.path.append(os.path.join(os.path.dirname(__file__), "src"))
-
-from typing import Tuple, List, Optional
-from maihem.api import MaihemHTTPClientSync
-from maihem.clients import Maihem
-
-maihem_client = Maihem()
-
-maihem_client._override_base_url(base_url="http://localhost:8000")
-maihem_client._override_base_url_ui(base_url_ui="http://localhost:3000")
-
-
-def chat_function_colin(
-    conversation_id: str,
-    agent_maihem_message: str,
-) -> Tuple[str, List[str]]:
-
-    url = "http://localhost:8002/chat?use_db=false"
-
-    payload = json.dumps(
-        {
-            "conversation_id": conversation_id,
-            "message": agent_maihem_message,
-        }
-    )
-    headers = {"Content-Type": "application/json"}
-
-    response = requests.request("POST", url, headers=headers, data=payload)
-
-    response_dict = response.json()
-
-    return response_dict["message"], response_dict["contexts"]
-
-
-# target_agent = maihem_client.create_target_agent(
-#     identifier="agent-colin-local",
-#     name="Colin Local",
-#     industry="Tech",
-#     description="A helpful customer support agent for a tech company.",
-#     role="customer_support",
-#     language="en",
-# )
-
-target_agent = maihem_client.get_target_agent("agent-colin-local")
-
-target_agent.set_chat_function(chat_function=chat_function_colin)
-
-# # target_agent.add_documents(["/Users/simon/Downloads/test1.pdf"])
-
-# test = maihem_client.create_test(
-#     identifier="test-result-refactor-2",
-#     target_agent_identifier="agent-colin-airbnb",
-#     name="Test result refactor",
-#     initiating_agent="maihem",
-#     maihem_agent_behavior_prompt="You are a customer of Airbnb having issues with your accommodation.",
-#     conversation_turns_max=5,
-#     metrics_config={
-#         "qa_cx_helpfulness": 2,
-#         "qa_cx_goal_completion": 2,
-#         "qa_rag_hallucination": 2,
-#     },
-# )
-
-test = maihem_client.get_test("test-result-refactor-2")
-
-test_run = maihem_client.create_test_run(
-    test_identifier="test-result-refactor-2",
-    target_agent=target_agent,
-    concurrent_conversations=2,
-)
-
-test_run = maihem_client.get_test_run_result(test_run_id=test_run.id)
-
-# print(test_run)