From 2ce2badadd31be56a52b47ed36333ef1ea6ddc35 Mon Sep 17 00:00:00 2001 From: Abram Date: Wed, 13 Dec 2023 15:57:16 +0100 Subject: [PATCH 01/11] Feat - implemented BinaryParam SDK type and BoolMeta class --- agenta-cli/agenta/__init__.py | 1 + agenta-cli/agenta/sdk/__init__.py | 1 + agenta-cli/agenta/sdk/types.py | 35 ++++++++++++++++++++++++++++++- 3 files changed, 36 insertions(+), 1 deletion(-) diff --git a/agenta-cli/agenta/__init__.py b/agenta-cli/agenta/__init__.py index b73eb24d60..9ca0db9841 100644 --- a/agenta-cli/agenta/__init__.py +++ b/agenta-cli/agenta/__init__.py @@ -10,6 +10,7 @@ MessagesInput, TextParam, FileInputURL, + BinaryParam ) from .sdk.utils.preinit import PreInitObject from .sdk.agenta_init import Config, init diff --git a/agenta-cli/agenta/sdk/__init__.py b/agenta-cli/agenta/sdk/__init__.py index b10b8c1e17..5cd129ea3d 100644 --- a/agenta-cli/agenta/sdk/__init__.py +++ b/agenta-cli/agenta/sdk/__init__.py @@ -12,6 +12,7 @@ TextParam, MessagesInput, FileInputURL, + BinaryParam ) from .agenta_init import Config, init diff --git a/agenta-cli/agenta/sdk/types.py b/agenta-cli/agenta/sdk/types.py index 8c22032bf8..ade31a5d33 100644 --- a/agenta-cli/agenta/sdk/types.py +++ b/agenta-cli/agenta/sdk/types.py @@ -1,7 +1,7 @@ import json from typing import Any, Dict, List -from pydantic import BaseModel, Extra, HttpUrl +from pydantic import BaseModel, Extra, HttpUrl, Field class InFile: @@ -29,6 +29,39 @@ def __modify_schema__(cls, field_schema): field_schema.update({"x-parameter": "text"}) +class BinaryParamMixin(BaseModel): + default: bool + + @property + def type(self) -> bool: + return "bool" + + +class BoolMeta(type): + """ + This meta class handles the behavior of a boolean without + directly inheriting from it (avoiding the conflict + that comes from inheriting bool). + """ + + def __new__(cls, name: str, bases: tuple, namespace: dict): + if "default" in namespace and namespace["default"] not in [0, 1]: + raise ValueError("Must provide either 0 or 1") + namespace["default"] = bool(namespace.get("default", 0)) + return super().__new__(cls, name, bases, namespace) + + +class BinaryParam(int, metaclass=BoolMeta): + @classmethod + def __modify_schema__(cls, field_schema): + field_schema.update( + { + "x-parameter": "bool", + "type": "boolean", + } + ) + + class IntParam(int): def __new__(cls, default: int = 6, minval: float = 1, maxval: float = 10): instance = super().__new__(cls, default) From ff9c6ad752f16555094d066fae1a5edefe67714b Mon Sep 17 00:00:00 2001 From: Abram Date: Wed, 13 Dec 2023 15:57:39 +0100 Subject: [PATCH 02/11] Update - override BinaryParam subschema --- agenta-cli/agenta/sdk/agenta_decorator.py | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/agenta-cli/agenta/sdk/agenta_decorator.py b/agenta-cli/agenta/sdk/agenta_decorator.py index e132b084a1..0042e765fe 100644 --- a/agenta-cli/agenta/sdk/agenta_decorator.py +++ b/agenta-cli/agenta/sdk/agenta_decorator.py @@ -26,6 +26,7 @@ TextParam, MessagesInput, FileInputURL, + BinaryParam, ) app = FastAPI() @@ -316,6 +317,7 @@ def override_schema(openapi_schema: dict, func_name: str, endpoint: str, params: - The default value for DictInput instance - The default value for MessagesParam instance - The default value for FileInputURL instance + - The default value for BinaryParam instance - ... [PLEASE ADD AT EACH CHANGE] Args: @@ -388,3 +390,6 @@ def find_in_schema(schema: dict, param_name: str, xparam: str): ): subschema = find_in_schema(schema_to_override, param_name, "file_url") subschema["default"] = "https://example.com" + if isinstance(param_val, BinaryParam): + subschema = find_in_schema(schema_to_override, param_name, "bool") + subschema["default"] = True if param_val.default == 1 else False From 6be1be22cae0a546ba44991562d4e7335c479e05 Mon Sep 17 00:00:00 2001 From: Abram Date: Wed, 13 Dec 2023 21:06:38 +0100 Subject: [PATCH 03/11] Update - determine bool type for playground use --- agenta-web/src/lib/helpers/openapi_parser.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/agenta-web/src/lib/helpers/openapi_parser.ts b/agenta-web/src/lib/helpers/openapi_parser.ts index 54d7dd34b7..02a3100d68 100644 --- a/agenta-web/src/lib/helpers/openapi_parser.ts +++ b/agenta-web/src/lib/helpers/openapi_parser.ts @@ -63,6 +63,8 @@ const determineType = (xParam: any): string => { return "number" case "dict": return "object" + case "bool": + return "boolean" case "int": return "integer" case "file_url": From 23db71e6b00a0e5c8997e409eb1f0064a5743ffc Mon Sep 17 00:00:00 2001 From: Abram Date: Wed, 13 Dec 2023 22:12:55 +0100 Subject: [PATCH 04/11] Update - include parameter switch ui for boolean param type --- .../Playground/Views/ParametersCards.tsx | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) diff --git a/agenta-web/src/components/Playground/Views/ParametersCards.tsx b/agenta-web/src/components/Playground/Views/ParametersCards.tsx index e18a6a570d..53355beccc 100644 --- a/agenta-web/src/components/Playground/Views/ParametersCards.tsx +++ b/agenta-web/src/components/Playground/Views/ParametersCards.tsx @@ -1,8 +1,8 @@ -import {Row, Card, Slider, Select, InputNumber, Col, Input, Button} from "antd" import React from "react" -import {Parameter, InputParameter} from "@/lib/Types" -import {renameVariables} from "@/lib/helpers/utils" import {createUseStyles} from "react-jss" +import {renameVariables} from "@/lib/helpers/utils" +import {Parameter, InputParameter} from "@/lib/Types" +import {Row, Card, Slider, Select, InputNumber, Col, Input, Button, Switch} from "antd" const useStyles = createUseStyles({ row1: { @@ -72,6 +72,10 @@ export const ModelParameters: React.FC = ({ handleParamChange, }) => { const classes = useStyles() + const handleCheckboxChange = (paramName: string, checked: boolean) => { + const value = checked ? 1 : 0 + handleParamChange(paramName, value) + } return ( <> {optParams?.some((param) => !param.input && param.type === "number") && ( @@ -83,7 +87,8 @@ export const ModelParameters: React.FC = ({ !param.input && (param.type === "number" || param.type === "integer" || - param.type === "array"), + param.type === "array") || + param.type === "boolean", ) .map((param, index) => ( @@ -136,6 +141,12 @@ export const ModelParameters: React.FC = ({ ))} )} + {param.type === "boolean" && ( + handleCheckboxChange(param.name, checked)} + /> + )} {param.type === "number" && ( From 5ba9a81fc4a9cee28e52ca5e69ff9b331eb28923 Mon Sep 17 00:00:00 2001 From: Abram Date: Thu, 14 Dec 2023 09:19:58 +0100 Subject: [PATCH 05/11] :art: Format - ran black and prettier --write . --- agenta-cli/agenta/__init__.py | 2 +- agenta-cli/agenta/sdk/__init__.py | 2 +- .../Playground/Views/ParametersCards.tsx | 14 ++++++++------ 3 files changed, 10 insertions(+), 8 deletions(-) diff --git a/agenta-cli/agenta/__init__.py b/agenta-cli/agenta/__init__.py index 9ca0db9841..8a683f19e1 100644 --- a/agenta-cli/agenta/__init__.py +++ b/agenta-cli/agenta/__init__.py @@ -10,7 +10,7 @@ MessagesInput, TextParam, FileInputURL, - BinaryParam + BinaryParam, ) from .sdk.utils.preinit import PreInitObject from .sdk.agenta_init import Config, init diff --git a/agenta-cli/agenta/sdk/__init__.py b/agenta-cli/agenta/sdk/__init__.py index 5cd129ea3d..ebd87f40ba 100644 --- a/agenta-cli/agenta/sdk/__init__.py +++ b/agenta-cli/agenta/sdk/__init__.py @@ -12,7 +12,7 @@ TextParam, MessagesInput, FileInputURL, - BinaryParam + BinaryParam, ) from .agenta_init import Config, init diff --git a/agenta-web/src/components/Playground/Views/ParametersCards.tsx b/agenta-web/src/components/Playground/Views/ParametersCards.tsx index 53355beccc..8a298e0d70 100644 --- a/agenta-web/src/components/Playground/Views/ParametersCards.tsx +++ b/agenta-web/src/components/Playground/Views/ParametersCards.tsx @@ -84,11 +84,11 @@ export const ModelParameters: React.FC = ({ {optParams ?.filter( (param) => - !param.input && - (param.type === "number" || - param.type === "integer" || - param.type === "array") || - param.type === "boolean", + (!param.input && + (param.type === "number" || + param.type === "integer" || + param.type === "array")) || + param.type === "boolean", ) .map((param, index) => ( @@ -144,7 +144,9 @@ export const ModelParameters: React.FC = ({ {param.type === "boolean" && ( handleCheckboxChange(param.name, checked)} + onChange={(checked: boolean) => + handleCheckboxChange(param.name, checked) + } /> )} From 96ff22f12461b29ffeb666ef78239301dccbbed5 Mon Sep 17 00:00:00 2001 From: Abram Date: Thu, 14 Dec 2023 18:56:45 +0100 Subject: [PATCH 06/11] Cleanup - remove BinaryParamMixin type --- agenta-cli/agenta/sdk/types.py | 8 -------- 1 file changed, 8 deletions(-) diff --git a/agenta-cli/agenta/sdk/types.py b/agenta-cli/agenta/sdk/types.py index ade31a5d33..05d59ad2d4 100644 --- a/agenta-cli/agenta/sdk/types.py +++ b/agenta-cli/agenta/sdk/types.py @@ -29,14 +29,6 @@ def __modify_schema__(cls, field_schema): field_schema.update({"x-parameter": "text"}) -class BinaryParamMixin(BaseModel): - default: bool - - @property - def type(self) -> bool: - return "bool" - - class BoolMeta(type): """ This meta class handles the behavior of a boolean without From 0e7f7cd36d51204639f5f3d36bc1efa851d9f3ad Mon Sep 17 00:00:00 2001 From: Abram Date: Thu, 14 Dec 2023 19:13:45 +0100 Subject: [PATCH 07/11] Update - added default value to BoolMeta instance --- agenta-cli/agenta/sdk/types.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/agenta-cli/agenta/sdk/types.py b/agenta-cli/agenta/sdk/types.py index 05d59ad2d4..3dc07cb6ef 100644 --- a/agenta-cli/agenta/sdk/types.py +++ b/agenta-cli/agenta/sdk/types.py @@ -40,7 +40,9 @@ def __new__(cls, name: str, bases: tuple, namespace: dict): if "default" in namespace and namespace["default"] not in [0, 1]: raise ValueError("Must provide either 0 or 1") namespace["default"] = bool(namespace.get("default", 0)) - return super().__new__(cls, name, bases, namespace) + instance = super().__new__(cls, name, bases, namespace) + instance.default = 0 + return instance class BinaryParam(int, metaclass=BoolMeta): From d7b18d582da0e8a7f2f00c35af718960087db1b9 Mon Sep 17 00:00:00 2001 From: Abram Date: Fri, 15 Dec 2023 08:30:34 +0100 Subject: [PATCH 08/11] Update - modified handle checkbox change function --- agenta-web/src/components/Playground/Views/ParametersCards.tsx | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/agenta-web/src/components/Playground/Views/ParametersCards.tsx b/agenta-web/src/components/Playground/Views/ParametersCards.tsx index 8a298e0d70..6006ce1349 100644 --- a/agenta-web/src/components/Playground/Views/ParametersCards.tsx +++ b/agenta-web/src/components/Playground/Views/ParametersCards.tsx @@ -73,8 +73,7 @@ export const ModelParameters: React.FC = ({ }) => { const classes = useStyles() const handleCheckboxChange = (paramName: string, checked: boolean) => { - const value = checked ? 1 : 0 - handleParamChange(paramName, value) + handleParamChange(paramName, checked) } return ( <> From 47aeb238a06b4327cdae22be81e6e02c0c620fe4 Mon Sep 17 00:00:00 2001 From: Abram Date: Fri, 15 Dec 2023 08:38:22 +0100 Subject: [PATCH 09/11] Feat - created llm example app for binaryparam --- examples/chat_json_format/app.py | 43 ++++++++++++++++++++++ examples/chat_json_format/requirements.txt | 2 + 2 files changed, 45 insertions(+) create mode 100644 examples/chat_json_format/app.py create mode 100644 examples/chat_json_format/requirements.txt diff --git a/examples/chat_json_format/app.py b/examples/chat_json_format/app.py new file mode 100644 index 0000000000..8f9d234480 --- /dev/null +++ b/examples/chat_json_format/app.py @@ -0,0 +1,43 @@ +import agenta as ag +from agenta.sdk.types import BinaryParam +from openai import OpenAI + +client = OpenAI() + +SYSTEM_PROMPT = "You have expertise in offering technical ideas to startups. Responses should be in json." +GPT_FORMAT_RESPONSE = ["gpt-3.5-turbo-1106", "gpt-4-1106-preview"] +CHAT_LLM_GPT = [ + "gpt-3.5-turbo-16k", + "gpt-3.5-turbo-0301", + "gpt-3.5-turbo-0613", + "gpt-3.5-turbo-16k-0613", + "gpt-4", +] + GPT_FORMAT_RESPONSE + +ag.init() +ag.config.default( + temperature=ag.FloatParam(0.2), + model=ag.MultipleChoiceParam("gpt-3.5-turbo", CHAT_LLM_GPT), + max_tokens=ag.IntParam(-1, -1, 4000), + prompt_system=ag.TextParam(SYSTEM_PROMPT), + force_json_response=BinaryParam(), +) + + +@ag.entrypoint +def chat(inputs: ag.MessagesInput = ag.MessagesInput()): + messages = [{"role": "system", "content": ag.config.prompt_system}] + inputs + max_tokens = ag.config.max_tokens if ag.config.max_tokens != -1 else None + response_format = ( + {"type": "json_object"} + if ag.config.force_json_response and ag.config.model in GPT_FORMAT_RESPONSE + else {"type": "text"} + ) + chat_completion = client.chat.completions.create( + model=ag.config.model, + messages=messages, + temperature=ag.config.temperature, + max_tokens=max_tokens, + response_format=response_format, + ) + return chat_completion.choices[0].message.content diff --git a/examples/chat_json_format/requirements.txt b/examples/chat_json_format/requirements.txt new file mode 100644 index 0000000000..310f162cec --- /dev/null +++ b/examples/chat_json_format/requirements.txt @@ -0,0 +1,2 @@ +agenta +openai \ No newline at end of file From 61b09d12c25e9f35fc8c53c92ebac47f0abee3a4 Mon Sep 17 00:00:00 2001 From: Abram Date: Fri, 15 Dec 2023 08:41:18 +0100 Subject: [PATCH 10/11] Update - modified handle checkbox change function to fix lint error --- agenta-web/src/components/Playground/Views/ParametersCards.tsx | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/agenta-web/src/components/Playground/Views/ParametersCards.tsx b/agenta-web/src/components/Playground/Views/ParametersCards.tsx index 6006ce1349..8a298e0d70 100644 --- a/agenta-web/src/components/Playground/Views/ParametersCards.tsx +++ b/agenta-web/src/components/Playground/Views/ParametersCards.tsx @@ -73,7 +73,8 @@ export const ModelParameters: React.FC = ({ }) => { const classes = useStyles() const handleCheckboxChange = (paramName: string, checked: boolean) => { - handleParamChange(paramName, checked) + const value = checked ? 1 : 0 + handleParamChange(paramName, value) } return ( <> From 920a2c0f76bbedc48e5e94bedd46f81902b3d741 Mon Sep 17 00:00:00 2001 From: Abram Date: Tue, 19 Dec 2023 09:52:03 +0100 Subject: [PATCH 11/11] Update - make use of 1/0 in BinaryParam default --- agenta-cli/agenta/sdk/agenta_decorator.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/agenta-cli/agenta/sdk/agenta_decorator.py b/agenta-cli/agenta/sdk/agenta_decorator.py index 0042e765fe..02565da2cd 100644 --- a/agenta-cli/agenta/sdk/agenta_decorator.py +++ b/agenta-cli/agenta/sdk/agenta_decorator.py @@ -392,4 +392,4 @@ def find_in_schema(schema: dict, param_name: str, xparam: str): subschema["default"] = "https://example.com" if isinstance(param_val, BinaryParam): subschema = find_in_schema(schema_to_override, param_name, "bool") - subschema["default"] = True if param_val.default == 1 else False + subschema["default"] = param_val.default