From c676d0eef7db0467a4b85545c45f500d2418a7c5 Mon Sep 17 00:00:00 2001 From: rjambrecic <32619626+rjambrecic@users.noreply.github.com> Date: Thu, 6 Jun 2024 09:09:40 +0200 Subject: [PATCH 1/4] 720 use gpt-4o for the brief creation team (#746) * Use gpt-4o for the brief creation team * Don't allow the usage of the incorrect customer_id in the ask client for permission fucntion * Prompt updates and cleanup --- .../captn_agents/backend/benchmarking/base.py | 2 +- .../benchmarking/brief_creation_team.py | 2 +- .../benchmarking/campaign_creation_team.py | 9 ++++++-- .../backend/benchmarking/end2end.py | 4 +--- .../backend/teams/_brief_creation_team.py | 14 +++++++---- .../captn_agents/backend/tools/_functions.py | 18 +++++++++++++-- .../backend/teams/test_brief_creation_team.py | 2 +- .../backend/tools/test_functions.py | 23 +++++++++++++++++++ 8 files changed, 60 insertions(+), 14 deletions(-) diff --git a/captn/captn_agents/backend/benchmarking/base.py b/captn/captn_agents/backend/benchmarking/base.py index c6c22f10..8833f710 100755 --- a/captn/captn_agents/backend/benchmarking/base.py +++ b/captn/captn_agents/backend/benchmarking/base.py @@ -132,7 +132,7 @@ def generate_task_table_for_websurfer( @app.command() def generate_task_table_for_brief_creation( llm: Models = typer.Option( # noqa: B008 - Models.gpt4, + Models.gpt4o, help="Model which will be used by all agents", ), file_name: str = typer.Option( diff --git a/captn/captn_agents/backend/benchmarking/brief_creation_team.py b/captn/captn_agents/backend/benchmarking/brief_creation_team.py index ac3ac645..d9a53c11 100644 --- a/captn/captn_agents/backend/benchmarking/brief_creation_team.py +++ b/captn/captn_agents/backend/benchmarking/brief_creation_team.py @@ -112,7 +112,7 @@ def _get_task(url: str) -> str: def benchmark_brief_creation( url: str, team_name: str, - llm: str = Models.gpt3_5, + llm: str = Models.gpt4o, ) -> Tuple[str, int]: config_list = get_config_list(llm) diff --git a/captn/captn_agents/backend/benchmarking/campaign_creation_team.py b/captn/captn_agents/backend/benchmarking/campaign_creation_team.py index 57a005a1..54f508f5 100644 --- a/captn/captn_agents/backend/benchmarking/campaign_creation_team.py +++ b/captn/captn_agents/backend/benchmarking/campaign_creation_team.py @@ -48,6 +48,7 @@ def mock_get_campaign_ids(context: Context, customer_id: str) -> List[str]: @contextmanager def _patch_campaign_creation_team_vars() -> Iterator[Tuple[Any, Any, Any, Any]]: + accessible_customers = ["1111"] with ( # unittest.mock.patch.object( # campaign_creation_team.toolbox.functions, @@ -56,7 +57,11 @@ def _patch_campaign_creation_team_vars() -> Iterator[Tuple[Any, Any, Any, Any]]: # ), unittest.mock.patch( "captn.captn_agents.backend.tools._google_ads_team_tools.list_accessible_customers_client", - return_value=["1111"], + return_value=accessible_customers, + ), + unittest.mock.patch( + "captn.captn_agents.backend.tools._functions.list_accessible_customers", + return_value=accessible_customers, ), # unittest.mock.patch.object( # campaign_creation_team.toolbox.functions, @@ -124,7 +129,7 @@ def _patch_campaign_creation_team_vars() -> Iterator[Tuple[Any, Any, Any, Any]]: ): mock_requests_get.return_value.ok = True mock_requests_get.return_value.json.side_effect = [ - f"Created resource/new/{random.randint(100, 1000)}" # nosec: [B311] + f"Created resource/{random.randint(100, 1000)}" # nosec: [B311] for _ in range(200) ] yield ( diff --git a/captn/captn_agents/backend/benchmarking/end2end.py b/captn/captn_agents/backend/benchmarking/end2end.py index b1b502ce..a6d0ceff 100644 --- a/captn/captn_agents/backend/benchmarking/end2end.py +++ b/captn/captn_agents/backend/benchmarking/end2end.py @@ -48,10 +48,8 @@ def _patch_brief_creation_team_vars( def benchmark_end2end( url: str, - llm: str = Models.gpt4, + llm: str = Models.gpt4o, ) -> Tuple[str, int]: - # Remove the following line after integrating gpt4-o for brief creation team - llm = Models.gpt4 config_list = get_config_list(llm) user_id = 123 diff --git a/captn/captn_agents/backend/teams/_brief_creation_team.py b/captn/captn_agents/backend/teams/_brief_creation_team.py index 52d4c994..3f258135 100644 --- a/captn/captn_agents/backend/teams/_brief_creation_team.py +++ b/captn/captn_agents/backend/teams/_brief_creation_team.py @@ -67,7 +67,7 @@ def __init__( if config_list is None: config = Config() - config_list = config.config_list_gpt_4 + config_list = config.config_list_gpt_4o self.llm_config = BriefCreationTeam._get_llm_config( seed=seed, temperature=temperature, config_list=config_list @@ -126,7 +126,7 @@ def _task(self) -> str: def _guidelines(self) -> str: return f"""### Guidelines 1. Do NOT repeat the content of the previous messages nor repeat your role. -Write short and clear messages. Nobody likes to read long messages. Be concise and to the point. +Write SHORT and CLEAR messages. Nobody likes to read long messages. Be concise and to the point, or you will be penalized! 2. The MOST important part of your task is to choose the appropriate team for the task. @@ -151,10 +151,16 @@ def _guidelines(self) -> str: 5. Use 'get_info_from_the_web_page' command to get information from the web page. This information MUST be used before creating the brief. It is MANADATORY to use this command to gather information if the client has provided a link to the web page. If the client has provided a link to the web page and you do not try to gather information from the web page, you will be penalized! -If you are unable to retrieve the information, use the 'reply_to_client' command to ask the client for the information which you need. +If you are unable to retrieve ANY information, use the 'reply_to_client' command to ask the client for the information which you need. +Otherwise, focus on creating the brief based on the information which you were able to gather from the web page (ignore the links which you were unable to retrieve information from and don't mention them in the brief!). +Do NOT use the 'get_info_from_the_web_page' for retrieving the information of the subpages which you have found in the provided link. +Your job is to create a brief based on the information which you have gathered from URL which the client has provided. +If you try to gather information from the subpages, a lot of time will be wasted and you will be penalized! +i.e. use the 'get_info_from_the_web_page' command ONLY once for the URL which the client has provided! 6. When you have gathered all the information, create a detailed brief. -Team members should discuss and agree on the content of the brief before sending it to the chosen team. +Do NOT repeat the content which you have received from the 'get_info_from_the_web_page' command (the content will be injected automatically later on)! +i.e. do NOT mention keywords, headlines and descriptions in the brief which you are constructing! Do NOT mention to the client that you are creating a brief. This is your internal task and the client does not need to know that. Do NOT ask the client which information he wants to include in the brief. i.e. word 'brief' should NOT be mentioned to the client at all! diff --git a/captn/captn_agents/backend/tools/_functions.py b/captn/captn_agents/backend/tools/_functions.py index aba6724d..d6aa41ca 100644 --- a/captn/captn_agents/backend/tools/_functions.py +++ b/captn/captn_agents/backend/tools/_functions.py @@ -27,7 +27,7 @@ from pydantic import BaseModel, Field, HttpUrl, ValidationError, field_validator from typing_extensions import _AnnotatedAlias -from ....google_ads.client import clean_nones, execute_query +from ....google_ads.client import clean_nones, execute_query, list_accessible_customers from ...model import SmartSuggestions from ..config import Config from ..toolboxes.base import Toolbox @@ -437,7 +437,7 @@ def ask_client_for_permission( modification_function_parameters_description, ], context: Context, -) -> str: +) -> Union[str, Dict[str, Any]]: try: func = context.toolbox.get_function(function_name) except Exception as e: @@ -459,6 +459,20 @@ def ask_client_for_permission( "The 'customer_id' parameter is missing in the 'modification_function_parameters'." ) + accessible_customer_ids = list_accessible_customers( + user_id=context.user_id, + conv_id=context.conv_id, + get_only_non_manager_accounts=context.get_only_non_manager_accounts, + ) + if not isinstance(accessible_customer_ids, list): + return accessible_customer_ids + + if customer_id not in accessible_customer_ids: + raise ValueError( + f"""Customer ID '{customer_id}' is not accessible for the current user. +Here is the list of accessible customer IDs: {accessible_customer_ids}""" + ) + for key in REMOVE_FROM_MODIFICATION_PARAMETERS: modification_function_parameters.pop(key, None) diff --git a/tests/ci/captn/captn_agents/backend/teams/test_brief_creation_team.py b/tests/ci/captn/captn_agents/backend/teams/test_brief_creation_team.py index 9c7b7079..f017fb87 100644 --- a/tests/ci/captn/captn_agents/backend/teams/test_brief_creation_team.py +++ b/tests/ci/captn/captn_agents/backend/teams/test_brief_creation_team.py @@ -58,5 +58,5 @@ def test_end2end_correct_team_choosed(self, team_name) -> None: benchmark_brief_creation( url="https://www.ikea.com/gb/en/", team_name=team_name, - llm=Models.gpt3_5, + llm=Models.gpt4o, ) diff --git a/tests/ci/captn/captn_agents/backend/tools/test_functions.py b/tests/ci/captn/captn_agents/backend/tools/test_functions.py index 62d4914d..6a978f81 100644 --- a/tests/ci/captn/captn_agents/backend/tools/test_functions.py +++ b/tests/ci/captn/captn_agents/backend/tools/test_functions.py @@ -23,6 +23,7 @@ _find_value_in_nested_dict, _get_campaign_ids, _validate_modification_parameters, + ask_client_for_permission, get_get_info_from_the_web_page, get_webpage_status_code, reply_to_client, @@ -315,6 +316,28 @@ def test_get_campaign_ids(self, execute_query_return_value, expected) -> None: == expected ) + def test_customer_id_not_in_accessible_customers(self) -> None: + toolbox = Toolbox() + toolbox.get_function = unittest.mock.MagicMock() + context = Context( + user_id=234, + conv_id=345, + recommended_modifications_and_answer_list=[], + toolbox=toolbox, + ) + with unittest.mock.patch( + "captn.captn_agents.backend.tools._functions.list_accessible_customers", + return_value=["1111"], + ): + with pytest.raises(ValueError) as e: + ask_client_for_permission( + resource_details="bla", + function_name="random_func", + modification_function_parameters={"customer_id": "2222"}, + context=context, + ) + assert "Customer ID '2222' is not accessible for the current user" in str(e) + @pytest.mark.parametrize( "proposed_user_actions", From 582cae08f5f4dcfb0f9ec7ce65eea2fdd67f58b4 Mon Sep 17 00:00:00 2001 From: rjambrecic <32619626+rjambrecic@users.noreply.github.com> Date: Thu, 6 Jun 2024 09:56:44 +0200 Subject: [PATCH 2/4] Disable code execution (#747) --- captn/captn_agents/backend/teams/_team.py | 5 +---- tests/ci/captn/captn_agents/backend/toolboxes/test_base.py | 2 +- .../backend/tools/test_brief_creation_team_tools.py | 2 +- .../backend/tools/test_campaign_creation_team_tools.py | 2 +- .../captn_agents/backend/tools/test_google_ads_team_tools.py | 2 +- .../backend/tools/test_weekly_analysis_team_tools.py | 2 +- 6 files changed, 6 insertions(+), 9 deletions(-) diff --git a/captn/captn_agents/backend/teams/_team.py b/captn/captn_agents/backend/teams/_team.py index 941f1c03..7ecdfa92 100644 --- a/captn/captn_agents/backend/teams/_team.py +++ b/captn/captn_agents/backend/teams/_team.py @@ -1,6 +1,5 @@ import datetime import json -import os import time import traceback from typing import Any, Callable, Dict, List, Optional, Tuple, Type, TypeVar @@ -16,8 +15,6 @@ _completions_create_original = autogen.oai.client.OpenAIClient.create -os.environ["AUTOGEN_USE_DOCKER"] = "no" - # WORKAROUND for consistent 500 error code when using openai functions @patch # type: ignore @@ -276,6 +273,7 @@ def _create_member( llm_config=False, system_message=system_message, is_termination_msg=self._is_termination_msg, + code_execution_config=False, ) return autogen.AssistantAgent( @@ -283,7 +281,6 @@ def _create_member( llm_config=self.llm_config, system_message=system_message, is_termination_msg=self._is_termination_msg, - code_execution_config={"work_dir": self.work_dir}, function_map=self.function_map, ) diff --git a/tests/ci/captn/captn_agents/backend/toolboxes/test_base.py b/tests/ci/captn/captn_agents/backend/toolboxes/test_base.py index 5d6b025c..33691e9a 100644 --- a/tests/ci/captn/captn_agents/backend/toolboxes/test_base.py +++ b/tests/ci/captn/captn_agents/backend/toolboxes/test_base.py @@ -285,7 +285,7 @@ def test_add_functions_to_agent_with_openai(self) -> None: "api_key": "dummy", # pragma: allowlist secret }, ) - user_proxy = UserProxyAgent(name="user_proxy") + user_proxy = UserProxyAgent(name="user_proxy", code_execution_config=False) toolbox = Toolbox() diff --git a/tests/ci/captn/captn_agents/backend/tools/test_brief_creation_team_tools.py b/tests/ci/captn/captn_agents/backend/tools/test_brief_creation_team_tools.py index f0f7f118..e84939a1 100644 --- a/tests/ci/captn/captn_agents/backend/tools/test_brief_creation_team_tools.py +++ b/tests/ci/captn/captn_agents/backend/tools/test_brief_creation_team_tools.py @@ -43,7 +43,7 @@ def setup(self) -> Iterator[None]: def test_llm_config(self) -> None: agent = AssistantAgent(name="agent", llm_config=self.llm_config) - user_proxy = UserProxyAgent(name="user_proxy") + user_proxy = UserProxyAgent(name="user_proxy", code_execution_config=False) self.toolbox.add_to_agent(agent, user_proxy) diff --git a/tests/ci/captn/captn_agents/backend/tools/test_campaign_creation_team_tools.py b/tests/ci/captn/captn_agents/backend/tools/test_campaign_creation_team_tools.py index 01e46711..56ca9852 100644 --- a/tests/ci/captn/captn_agents/backend/tools/test_campaign_creation_team_tools.py +++ b/tests/ci/captn/captn_agents/backend/tools/test_campaign_creation_team_tools.py @@ -39,7 +39,7 @@ def setup(self) -> None: def test_llm_config(self) -> None: agent = AssistantAgent(name="agent", llm_config=self.llm_config) - user_proxy = UserProxyAgent(name="user_proxy") + user_proxy = UserProxyAgent(name="user_proxy", code_execution_config=False) self.toolbox.add_to_agent(agent, user_proxy) llm_config = agent.llm_config diff --git a/tests/ci/captn/captn_agents/backend/tools/test_google_ads_team_tools.py b/tests/ci/captn/captn_agents/backend/tools/test_google_ads_team_tools.py index 81f73eaa..c64f904a 100644 --- a/tests/ci/captn/captn_agents/backend/tools/test_google_ads_team_tools.py +++ b/tests/ci/captn/captn_agents/backend/tools/test_google_ads_team_tools.py @@ -42,7 +42,7 @@ def setup(self) -> None: ) self.agent = AssistantAgent(name="agent", llm_config=self.llm_config) - self.user_proxy = UserProxyAgent(name="user_proxy") + self.user_proxy = UserProxyAgent(name="user_proxy", code_execution_config=False) self.toolbox.add_to_agent(self.agent, self.user_proxy) diff --git a/tests/ci/captn/captn_agents/backend/tools/test_weekly_analysis_team_tools.py b/tests/ci/captn/captn_agents/backend/tools/test_weekly_analysis_team_tools.py index e56f83a1..e52acfd4 100644 --- a/tests/ci/captn/captn_agents/backend/tools/test_weekly_analysis_team_tools.py +++ b/tests/ci/captn/captn_agents/backend/tools/test_weekly_analysis_team_tools.py @@ -31,7 +31,7 @@ def setup(self) -> None: ) self.agent = AssistantAgent(name="agent", llm_config=self.llm_config) - self.user_proxy = UserProxyAgent(name="user_proxy") + self.user_proxy = UserProxyAgent(name="user_proxy", code_execution_config=False) self.toolbox.add_to_agent(self.agent, self.user_proxy) From f7403e9ca15857ca5bb2d9a067513d7199916941 Mon Sep 17 00:00:00 2001 From: rjambrecic <32619626+rjambrecic@users.noreply.github.com> Date: Thu, 6 Jun 2024 13:38:23 +0200 Subject: [PATCH 3/4] Test 10 urls in benchmarks (#748) * Update benchmark.sh with option for running the benchmark for all teams * wip * Test 10 different urls in all benchmarks --- .../captn_agents/backend/benchmarking/base.py | 6 +- .../benchmarking/brief_creation_team.py | 10 + .../benchmarking/campaign_creation_team.py | 16 +- .../fixtures/brief_creation_team_fixtures.py | 160 ++++++++ .../campaign_creation_team_fixtures.py | 374 ++++++++++++++++++ scripts/benchmark.sh | 65 +-- .../backend/benchmarking/test_benchmarking.py | 4 +- 7 files changed, 600 insertions(+), 35 deletions(-) diff --git a/captn/captn_agents/backend/benchmarking/base.py b/captn/captn_agents/backend/benchmarking/base.py index 8833f710..82549e1b 100755 --- a/captn/captn_agents/backend/benchmarking/base.py +++ b/captn/captn_agents/backend/benchmarking/base.py @@ -90,7 +90,7 @@ def generate_task_table_for_websurfer( help="File name of the task list", ), repeat: int = typer.Option( - 10, + 5, help="Number of times to repeat each url", ), introduce_give_up_after: int = typer.Option( @@ -140,7 +140,7 @@ def generate_task_table_for_brief_creation( help="File name of the task list", ), repeat: int = typer.Option( - 10, + 5, help="Number of times to repeat each url", ), output_dir: str = typer.Option( # noqa: B008 @@ -182,7 +182,7 @@ def generate_task_table_for_campaign_creation( help="File name of the task list", ), repeat: int = typer.Option( - 10, + 5, help="Number of times to repeat each url", ), output_dir: str = typer.Option( # noqa: B008 diff --git a/captn/captn_agents/backend/benchmarking/brief_creation_team.py b/captn/captn_agents/backend/benchmarking/brief_creation_team.py index d9a53c11..9be66e4f 100644 --- a/captn/captn_agents/backend/benchmarking/brief_creation_team.py +++ b/captn/captn_agents/backend/benchmarking/brief_creation_team.py @@ -11,11 +11,16 @@ ) from .fixtures.brief_creation_team_fixtures import ( BRIEF_CREATION_TEAM_RESPONSE, + WEB_PAGE_SUMMARY_BBC, + WEB_PAGE_SUMMARY_CINESTAR, WEB_PAGE_SUMMARY_DISNEY, WEB_PAGE_SUMMARY_FASTSTREAM, + WEB_PAGE_SUMMARY_FLOWERSHOP, + WEB_PAGE_SUMMARY_GET_BY_BUS, WEB_PAGE_SUMMARY_HAMLEYS, WEB_PAGE_SUMMARY_IKEA, WEB_PAGE_SUMMARY_KONZUM, + WEB_PAGE_SUMMARY_WEBSITE_DEMOS, ) from .helpers import get_client_response, get_config_list from .models import Models @@ -32,6 +37,11 @@ "https://www.hamleys.com/": WEB_PAGE_SUMMARY_HAMLEYS, "https://www.konzum.hr": WEB_PAGE_SUMMARY_KONZUM, "https://faststream.airt.ai": WEB_PAGE_SUMMARY_FASTSTREAM, + "https://camelbackflowershop.com": WEB_PAGE_SUMMARY_FLOWERSHOP, + "https://www.bbc.com": WEB_PAGE_SUMMARY_BBC, + "https://zagreb.cinestarcinemas.hr": WEB_PAGE_SUMMARY_CINESTAR, + "https://websitedemos.net/organic-shop-02": WEB_PAGE_SUMMARY_WEBSITE_DEMOS, + "https://getbybus.com/hr": WEB_PAGE_SUMMARY_GET_BY_BUS, } diff --git a/captn/captn_agents/backend/benchmarking/campaign_creation_team.py b/captn/captn_agents/backend/benchmarking/campaign_creation_team.py index 54f508f5..6460f32d 100644 --- a/captn/captn_agents/backend/benchmarking/campaign_creation_team.py +++ b/captn/captn_agents/backend/benchmarking/campaign_creation_team.py @@ -21,9 +21,16 @@ from ..tools._functions import Context from ..tools._google_ads_team_tools import _mock_create_campaign from .fixtures.campaign_creation_team_fixtures import ( + CAMPAIGN_CREATION_BBC, + CAMPAIGN_CREATION_CINESTAR, CAMPAIGN_CREATION_DISNEY, CAMPAIGN_CREATION_FASTSTREAM, + CAMPAIGN_CREATION_FLOWERSHOP, + CAMPAIGN_CREATION_GETBYBUS, + CAMPAIGN_CREATION_HAMLEYS, CAMPAIGN_CREATION_IKEA, + CAMPAIGN_CREATION_KONZUM, + CAMPAIGN_CREATION_WEBSITEDEMOS, ) from .helpers import get_client_response_for_the_team_conv, get_config_list from .models import Models @@ -31,9 +38,14 @@ URL_TASK_DICT = { "https://www.ikea.com/gb/en/": CAMPAIGN_CREATION_IKEA, "https://www.disneystore.eu": CAMPAIGN_CREATION_DISNEY, - # "https://www.hamleys.com/": "", - # "https://www.konzum.hr": "", "https://faststream.airt.ai": CAMPAIGN_CREATION_FASTSTREAM, + "https://www.hamleys.com/": CAMPAIGN_CREATION_HAMLEYS, + "https://www.konzum.hr": CAMPAIGN_CREATION_KONZUM, + "https://websitedemos.net/organic-shop-02/": CAMPAIGN_CREATION_WEBSITEDEMOS, + "www.bbc.com/news": CAMPAIGN_CREATION_BBC, + "https://zagreb.cinestarcinemas.hr/": CAMPAIGN_CREATION_CINESTAR, + "https://camelbackflowershop.com/": CAMPAIGN_CREATION_FLOWERSHOP, + "https://getbybus.com/hr/": CAMPAIGN_CREATION_GETBYBUS, } diff --git a/captn/captn_agents/backend/benchmarking/fixtures/brief_creation_team_fixtures.py b/captn/captn_agents/backend/benchmarking/fixtures/brief_creation_team_fixtures.py index da928484..80702c1a 100644 --- a/captn/captn_agents/backend/benchmarking/fixtures/brief_creation_team_fixtures.py +++ b/captn/captn_agents/backend/benchmarking/fixtures/brief_creation_team_fixtures.py @@ -5,6 +5,11 @@ "WEB_PAGE_SUMMARY_HAMLEYS", "WEB_PAGE_SUMMARY_KONZUM", "WEB_PAGE_SUMMARY_FASTSTREAM", + "WEB_PAGE_SUMMARY_FLOWERSHOP", + "WEB_PAGE_SUMMARY_BBC", + "WEB_PAGE_SUMMARY_WEBSITE_DEMOS", + "WEB_PAGE_SUMMARY_CINESTAR", + "WEB_PAGE_SUMMARY_GET_BY_BUS", ) BRIEF_CREATION_TEAM_RESPONSE = r"""{"message":"Here is the list of all customer IDs accessible to you:\n- 7119828439\n- 7587037554","smart_suggestions":{"suggestions":[""],"type":""},"is_question":true,"status":"completed","terminate_groupchat":true}""" @@ -232,3 +237,158 @@ Headlines: 'API Documentation', 'Class References', 'Function Details', 'Middleware Info', 'API Usage Guide', 'Developer Resources', 'Code Examples', 'API Integration', 'FastStream API', 'Technical Specs', 'Middleware Hooks', 'API Customization', 'Advanced Usage', 'API Best Practices', 'Detailed Guides' Descriptions: 'Detailed API documentation.', ""Explore FastStream's API."", 'Guides for API integration.', 'Resources for developers.' """ + +WEB_PAGE_SUMMARY_FLOWERSHOP = """Here is a summary of the information you requested: + +Camelback Flowershop offers a variety of products including flowers, wine, gift boxes, and plants. They provide same-day delivery for orders placed before 2 PM. Their unique selling points include designer's choice floral arrangements, wine and flower combinations, and a wide range of gift boxes for different occasions. + +Relevant Pages: + +1. Wine & Flowers: + URL: https://camelbackflowershop.com/collections/wine + Summary: Combination of wine and flowers + Keywords: 'Wine & Flowers', 'Gift Sets', 'Same-Day Delivery', 'Phoenix', 'Luxury Gifts' + Headlines: 'Elegant Wine & Flower Sets', 'Same-Day {Keyword:Delivery}', 'Luxury Wine & Flower Gifts', 'Perfect for Any Occasion', 'Wine & Flowers in Phoenix', 'Unique Gift Combinations', 'Order Wine & Flowers Today', 'Premium Wine & Floral Sets', 'Gift Wine & Flowers Now', 'Wine & Flowers Delivered', 'Exclusive Wine & Flowers', 'Wine & Flowers for Events', 'Best Wine & Flower Gifts', 'Wine & Flowers for Romance', 'Wine & Flowers for Sympathy' + Descriptions: 'Elegant wine and flower sets for any occasion.', 'Same-day delivery available in Phoenix.', 'Luxury gifts combining wine and flowers.', 'Perfect for romantic or sympathy gestures.' + +2. Gift Boxes: + URL: https://camelbackflowershop.com/collections/gift-box-collection + Summary: Variety of gift boxes + Keywords: 'Gift Boxes', 'Luxury Gifts', 'Same-Day Delivery', 'Phoenix', 'Special Occasions' + Headlines: 'Luxury Gift Boxes', 'Same-Day {Keyword:Delivery}', 'Gift Boxes for All Occasions', 'Unique Gift Box Sets', 'Gift Boxes in Phoenix', 'Order Gift Boxes Today', 'Premium Gift Box Collection', 'Exclusive Gift Boxes', 'Gift Boxes for Special Events', 'Best Gift Box Sets', 'Gift Boxes for Romance', 'Gift Boxes for Sympathy', 'Gift Boxes for Birthdays', 'Gift Boxes for Anniversaries', 'Gift Boxes for Holidays' + Descriptions: 'Luxury gift boxes for all occasions.', 'Same-day delivery available in Phoenix.', 'Unique gift box sets for special events.', 'Perfect for birthdays, anniversaries, and holidays.' + +3. Plants: + URL: https://camelbackflowershop.com/collections/all-plants + Summary: Variety of plants + Keywords: 'Plants', 'Succulents', 'Cacti', 'Orchids', 'Same-Day Delivery', 'Phoenix' + Headlines: 'Beautiful Plants', 'Same-Day {Keyword:Delivery}', 'Succulents & Cacti', 'Orchids & More', 'Plants in Phoenix', 'Order Plants Today', 'Premium Plant Collection', 'Exclusive Plant Varieties', 'Plants for Home & Office', 'Best Plant Selection', 'Plants for Gifts', 'Plants for Decor', 'Plants for Events', 'Plants for Sympathy', 'Plants for Romance' + Descriptions: 'Beautiful plants for home and office.', 'Same-day delivery available in Phoenix.', 'Wide variety of succulents, cacti, and orchids.', 'Perfect for gifts, decor, and events.' +""" + +WEB_PAGE_SUMMARY_BBC = """Here is a summary of the information you requested: + +Page content: BBC Sport offers comprehensive coverage of various sports including football, cricket, Formula 1, rugby, tennis, golf, athletics, and cycling. The website provides live scores, fixtures, results, and video highlights. It also features news articles, player profiles, and in-depth analysis. Unique selling points include real-time updates, extensive coverage of major sports events, and a user-friendly interface. + +Relevant Pages: + +1. Football: + URL: https://www.bbc.com/sport/football + Summary: Latest news, scores, fixtures, and video highlights for football. + Keywords: 'Football', 'Live Scores', 'Fixtures', 'Results', 'Video Highlights', 'Premier League', 'UEFA', 'Champions League', 'Transfers', 'Top Scorers', "Women's Football", 'European Football', 'Teams', 'Leagues', 'Cups' + Headlines: 'Live Football Scores & Updates', 'Latest Football News Today', 'Football Fixtures & Results', 'Watch Football Video Highlights', 'Premier League News & Updates', 'UEFA Champions League News', 'Football Transfer News', 'Top Scorers in Football', "Women's Football News", 'European Football Updates', 'All Football Teams & Leagues', 'Football Leagues & Cups', 'Football Gossip & Rumors', 'Football Match Previews', '{Keyword: Football News}' + Descriptions: 'Get live football scores and updates.', 'Read the latest football news today.', 'Check football fixtures and results.', 'Watch video highlights of football matches.' + +2. UEFA Euro 2024: + URL: https://www.bbc.com/sport/football/european-championship + Summary: News, qualifiers, scores, and fixtures for UEFA Euro 2024. + Keywords: 'UEFA Euro 2024', 'Euro 2024 News', 'Euro 2024 Qualifiers', 'Euro 2024 Scores', 'Euro 2024 Fixtures', 'Euro 2024 Results', 'Euro 2024 Teams', 'Euro 2024 Groups', 'Euro 2024 Tables', 'Euro 2024 Highlights', 'Euro 2024 Matches', 'Euro 2024 Schedule', 'Euro 2024 Updates', 'Euro 2024 Live', 'Euro 2024 Coverage' + Headlines: 'UEFA Euro 2024 News & Updates', 'Euro 2024 Qualifiers & Results', 'Live Scores for Euro 2024', 'Euro 2024 Fixtures & Schedule', 'Euro 2024 Teams & Groups', 'Euro 2024 Tables & Standings', 'Watch Euro 2024 Highlights', 'Euro 2024 Match Previews', 'Euro 2024 Live Coverage', 'Latest Euro 2024 News', 'Euro 2024 Player Profiles', 'Euro 2024 Match Analysis', 'Euro 2024 Tournament Updates', 'Euro 2024 Fan Reactions', '{Keyword: Euro 2024 News}' + Descriptions: 'Get the latest news and updates on UEFA Euro 2024.', 'Check Euro 2024 qualifiers and results.', 'Find live scores for Euro 2024 matches.', 'View fixtures and schedule for Euro 2024.' + +3. UEFA Euro 2024 Scores & Fixtures: + URL: https://www.bbc.com/sport/football/european-championship/scores-fixtures + Summary: Scores and fixtures for UEFA Euro 2024. + Keywords: 'Euro 2024 Scores', 'Euro 2024 Fixtures', 'Euro 2024 Schedule', 'Euro 2024 Matches', 'Euro 2024 Results', 'Euro 2024 Live Scores', 'Euro 2024 Updates', 'Euro 2024 Calendar', 'Euro 2024 Match Dates', 'Euro 2024 Game Times', 'Euro 2024 Match Schedule', 'Euro 2024 Fixtures List', 'Euro 2024 Match Fixtures', 'Euro 2024 Live Updates', 'Euro 2024 Match Results' + Headlines: 'Euro 2024 Scores & Fixtures', 'Live Scores for Euro 2024', 'Euro 2024 Match Schedule', 'Euro 2024 Fixtures List', 'Euro 2024 Game Times', 'Euro 2024 Match Dates', 'Euro 2024 Live Updates', 'Euro 2024 Match Results', 'Euro 2024 Calendar', 'Euro 2024 Match Fixtures', 'Euro 2024 Fixtures & Results', 'Euro 2024 Live Match Scores', 'Euro 2024 Match Times', 'Euro 2024 Schedule & Updates', '{Keyword: Euro 2024 Scores}' + Descriptions: 'Find scores and fixtures for UEFA Euro 2024.', 'Get live scores for Euro 2024 matches.', 'Check the match schedule for Euro 2024.', 'View the fixtures list for Euro 2024.' +""" + + +WEB_PAGE_SUMMARY_CINESTAR = """Here is a summary of the information you requested: + +CineStar Cinemas in Zagreb offers a variety of services including birthday party packages, school screenings, and online ticket purchasing. They provide different birthday packages with options for 2D and 4DX screenings, professional animators, and various menu choices. School screenings offer discounted tickets and menus for students, with free tickets and popcorn for teachers. The e-payment system allows for easy online ticket purchases with secure data handling. + +Relevant Pages: + +1. Dječji Rođendani: + URL: https://zagreb.cinestarcinemas.hr/djeca-i-obitelj/djecji-rodendani + Summary: Birthday party packages for children + Keywords: 'Birthday Parties', 'Kids Parties', 'CineStar Birthday', 'Birthday Packages', '4DX Birthday' + Headlines: 'Celebrate with {Keyword: CineStar}', 'Total Cool Birthday Party', 'Choose Your Birthday Package', 'Basic Birthday Package', 'Party in the Birthday Room', '4DX Birthday Package', 'Kids Hall Party', 'Mini Birthday Package', 'Cool Birthday Package', 'Movie Birthday Package', 'Professional Animator Service', 'Add 4DX Fun to Your Party', 'Add eXtreme Fun to Your Party', 'Add 3D Fun to Your Party', 'Add ScreenX Fun to Your Party' + Descriptions: 'Celebrate your birthday with a movie, popcorn, and friends at CineStar.', 'Choose from various birthday packages including 2D and 4DX screenings.', 'Add professional animators to make your party even more fun.', 'Enjoy special birthday menus and gifts for the birthday child.' + +2. Školske Projekcije: + URL: https://zagreb.cinestarcinemas.hr/djeca-i-obitelj/skolske-projekcije + Summary: School screenings with discounts + Keywords: 'School Screenings', 'Student Discounts', 'CineStar School', 'Educational Screenings', 'Group Discounts' + Headlines: 'School Screenings at CineStar', 'Discounted Tickets for Students', 'Free Tickets for Teachers', 'Enjoy Movies with Your Class', 'CinesCool Day', 'Organize a School Screening', 'Special Prices for Schools', 'Educational Movie Experience', 'Combine Fun and Learning', 'Group Discounts Available', 'Special Menus for Students', 'Free Popcorn for Teachers', 'Book Your School Screening', 'Enjoy IMAX Documentaries', 'Plan Your School Trip' + Descriptions: 'Organize a school trip to CineStar with discounted tickets and menus.', 'Teachers get free tickets and popcorn with school screenings.', 'Enjoy educational movies and special group discounts.', 'Book your school screening and enjoy a fun learning experience.' + +3. e-plaćanje: + URL: https://zagreb.cinestarcinemas.hr/e-placanje + Summary: Online ticket purchasing + Keywords: 'Online Ticket Purchase', 'e-Payment', 'CineStar Tickets', 'Secure Payment', 'Buy Tickets Online' + Headlines: 'Buy Tickets Online', 'Easy Online Ticket Purchase', 'Secure e-Payment System', 'Purchase Tickets from Home', 'Fast and Easy Ticket Buying', 'Enjoy Movies with e-Payment', 'Safe Online Transactions', 'Corvus Pay for Secure Payment', 'No Data Storage on Server', 'Register for Online Purchase', 'Secure Your Account', 'PIN Protection for Cards', 'Follow Security Guidelines', 'Enjoy Movies with Ease', 'Book Your Tickets Online' + Descriptions: 'Buy your CineStar tickets online quickly and securely.', 'Enjoy the convenience of e-payment for movie tickets.', 'Secure transactions with Corvus Pay system.', 'Register and follow security guidelines for safe purchases.'""" + + +WEB_PAGE_SUMMARY_WEBSITE_DEMOS = """Here is a summary of the information you requested: + +The Organic Store website offers a variety of organic products including groceries and juices. The store emphasizes quality with features like free shipping, certified organic products, huge savings, and easy returns. Popular products include assorted coffee, hand sanitizer, handpicked red chillies, natural extracted olive oil, and fresh orange juice. + +Relevant Pages: + +1. Shop - Organic Store: + URL: https://websitedemos.net/organic-shop-02/shop/ + Summary: Product pages for all items + Keywords: 'Organic Products', 'Groceries', 'Juices', 'Free Shipping', 'Certified Organic', 'Huge Savings' + Headlines: 'Shop the Best Organic Products', 'Discover Our Organic Selection', 'Certified Organic Products', 'Huge Savings on Organic Items', 'Free Shipping on Orders Over $5', 'Easy Returns on All Products', 'Join the Organic Movement', 'Shop Now for Organic Groceries', 'Fresh Organic Juices Available', 'Lowest Prices on Organic Goods', 'Top Quality Organic Products', 'Organic Groceries for Your Home', 'Healthy and Organic Choices', 'Save Big on Organic Products', '{Keyword: Organic Products}' + Descriptions: 'Explore our wide range of organic products.', 'Certified organic items with free shipping.', 'Huge savings on top-quality organic goods.', 'Easy returns on all organic products.' + +2. Groceries Archives - Organic Store: + URL: https://websitedemos.net/organic-shop-02/product-category/groceries/ + Summary: Product pages for groceries + Keywords: 'Organic Groceries', 'Healthy Food', 'Natural Products', 'Certified Organic', 'Free Shipping', 'Huge Savings' + Headlines: 'Shop Organic Groceries Now', 'Healthy Organic Groceries', 'Certified Organic Groceries', 'Free Shipping on Groceries', 'Huge Savings on Groceries', 'Top Quality Organic Groceries', 'Fresh and Natural Groceries', 'Organic Groceries for Your Home', 'Best Prices on Organic Groceries', 'Join the Organic Grocery Movement', 'Easy Returns on Groceries', 'Shop Now for Organic Groceries', 'Healthy Choices for Your Family', 'Save Big on Organic Groceries', '{Keyword: Organic Groceries}' + Descriptions: 'Discover our range of organic groceries.', 'Certified organic groceries with free shipping.', 'Huge savings on top-quality groceries.', 'Easy returns on all grocery items.' + +3. Juice Archives - Organic Store: + URL: https://websitedemos.net/organic-shop-02/product-category/juice/ + Summary: Product pages for juices + Keywords: 'Organic Juices', 'Healthy Drinks', 'Natural Juices', 'Certified Organic', 'Free Shipping', 'Huge Savings' + Headlines: 'Shop Organic Juices Now', 'Healthy Organic Juices', 'Certified Organic Juices', 'Free Shipping on Juices', 'Huge Savings on Juices', 'Top Quality Organic Juices', 'Fresh and Natural Juices', 'Organic Juices for Your Home', 'Best Prices on Organic Juices', 'Join the Organic Juice Movement', 'Easy Returns on Juices', 'Shop Now for Organic Juices', 'Healthy Drinks for Your Family', 'Save Big on Organic Juices', '{Keyword: Organic Juices}' + Descriptions: 'Discover our range of organic juices.', 'Certified organic juices with free shipping.', 'Huge savings on top-quality juices.', 'Easy returns on all juice products.' +""" + +WEB_PAGE_SUMMARY_GET_BY_BUS = """Here is a summary of the information you requested: + +GetByBus is a platform that simplifies bus travel by connecting 198,525 stations. It offers services such as finding bus stations, purchasing one-way and return tickets, and ensuring luggage safety during travel. The website provides detailed guides and blog posts to assist travelers. + +Relevant Pages: + +1. Pronađite autobusne kolodvore i stanice na GetByBus.com: + URL: https://getbybus.com/hr/station-locator + Summary: Locator for bus stations in various countries. + Keywords: 'Bus Stations', 'Travel', 'Locator', 'GetByBus', 'Bus Stops', 'Station Finder' + Headlines: 'Find Bus Stations Easily', 'Locate Bus Stops Quickly', 'Bus Stations Near You', 'Find {Keyword:Bus Stations}', 'Bus Station Locator', 'Search Bus Stations', 'Find Bus Stops', 'Locate {Keyword:Bus Stops}', 'Bus Stations Worldwide', 'Find Bus Stations Fast', 'Bus Station Finder', 'Locate Bus Stations', 'Find Bus Stops Easily', 'Search {Keyword:Bus Stops}', 'Bus Station Search' + Descriptions: 'Easily find bus stations near you.', 'Quickly locate bus stops worldwide.', 'Search for bus stations in various countries.', 'Find bus stops and stations easily.' + +2. Autobusne Stanice Hrvatska - Lista svih kolodvora: + URL: https://getbybus.com/hr/drzava/hrvatska/autobusne-stanice + Summary: List of all bus stations in Croatia. + Keywords: 'Croatia Bus Stations', 'Bus Stops Croatia', 'GetByBus Croatia', 'Bus Stations List', 'Croatia Travel' + Headlines: 'Croatia Bus Stations List', 'Find Bus Stations in Croatia', 'Croatia {Keyword:Bus Stations}', 'Bus Stops in Croatia', 'Locate Croatia Bus Stops', 'Find {Keyword:Bus Stops} in Croatia', 'Croatia Bus Station Finder', 'Search Bus Stations in Croatia', 'Croatia Bus Stops Locator', 'Find Bus Stations in {Keyword:Croatia}', 'Croatia Bus Stations Search', 'Locate Bus Stations in Croatia', 'Find Bus Stops in Croatia', 'Search {Keyword:Bus Stations} in Croatia', 'Croatia Bus Station Search' + Descriptions: 'Find all bus stations in Croatia.', 'Locate bus stops in Croatia easily.', 'Search for bus stations in Croatia.', 'Find bus stops and stations in Croatia.' + +3. Kupovina jednosmjerne autobusne karte na GetByBus-u - GetByBus Blog: + URL: https://getbybus.com/hr/blog/kupovina-jednosmjerne-autobusne-karte-na-getbybus-u/ + Summary: Guide on purchasing one-way bus tickets. + Keywords: 'One-Way Bus Tickets', 'GetByBus Tickets', 'Bus Travel', 'Ticket Purchase Guide', 'Bus Tickets' + Headlines: 'Buy One-Way Bus Tickets', 'Purchase {Keyword:Bus Tickets}', 'One-Way Tickets on GetByBus', 'GetByBus Ticket Guide', 'How to Buy Bus Tickets', 'One-Way Bus Ticket Purchase', 'Get {Keyword:Bus Tickets}', 'Buy Bus Tickets Easily', 'Purchase One-Way Tickets', 'GetByBus One-Way Tickets', 'Buy {Keyword:One-Way Tickets}', 'Bus Ticket Purchase Guide', 'Get Your Bus Tickets', 'Buy Tickets on GetByBus', 'One-Way Ticket Guide' + Descriptions: 'Guide to buying one-way bus tickets.', 'Purchase one-way bus tickets easily.', 'How to buy one-way bus tickets.', 'Get one-way bus tickets on GetByBus.' + +4. Kupovina povratne karte - GetByBus Blog: + URL: https://getbybus.com/hr/blog/kupovina-povratne-karte/ + Summary: Guide on purchasing return bus tickets. + Keywords: 'Return Bus Tickets', 'GetByBus Tickets', 'Bus Travel', 'Ticket Purchase Guide', 'Bus Tickets' + Headlines: 'Buy Return Bus Tickets', 'Purchase {Keyword:Bus Tickets}', 'Return Tickets on GetByBus', 'GetByBus Ticket Guide', 'How to Buy Bus Tickets', 'Return Bus Ticket Purchase', 'Get {Keyword:Bus Tickets}', 'Buy Bus Tickets Easily', 'Purchase Return Tickets', 'GetByBus Return Tickets', 'Buy {Keyword:Return Tickets}', 'Bus Ticket Purchase Guide', 'Get Your Bus Tickets', 'Buy Tickets on GetByBus', 'Return Ticket Guide' + Descriptions: 'Guide to buying return bus tickets.', 'Purchase return bus tickets easily.', 'How to buy return bus tickets.', 'Get return bus tickets on GetByBus.' + +5. Sigurnost prtljage tijekom putovanja autobusom - GetByBus Blog: + URL: https://getbybus.com/hr/blog/putovanje-autobusom-sa-prtljagom-u-inozemstvu/ + Summary: Guide on luggage safety during bus travel. + Keywords: 'Luggage Safety', 'Bus Travel', 'GetByBus Guide', 'Travel Tips', 'Bus Luggage' + Headlines: 'Luggage Safety Tips', 'Bus Travel {Keyword:Safety}', 'Keep Luggage Safe', 'GetByBus Luggage Guide', 'Luggage Safety on Buses', 'Travel with Safe Luggage', 'Bus Luggage Safety Tips', 'Keep {Keyword:Luggage Safe}', 'Safe Luggage Travel', 'Luggage Safety Guide', 'Bus Travel Tips', 'Safe Travel with Luggage', 'GetByBus Travel Guide', 'Luggage Safety Tips', 'Travel {Keyword:Safety} Tips' + Descriptions: 'Guide to luggage safety during bus travel.', 'Keep your luggage safe on buses.', 'Tips for safe luggage travel.', 'Ensure luggage safety during bus trips.' +""" diff --git a/captn/captn_agents/backend/benchmarking/fixtures/campaign_creation_team_fixtures.py b/captn/captn_agents/backend/benchmarking/fixtures/campaign_creation_team_fixtures.py index 40183968..dcd3e31b 100644 --- a/captn/captn_agents/backend/benchmarking/fixtures/campaign_creation_team_fixtures.py +++ b/captn/captn_agents/backend/benchmarking/fixtures/campaign_creation_team_fixtures.py @@ -2,6 +2,13 @@ "CAMPAIGN_CREATION_IKEA", "CAMPAIGN_CREATION_DISNEY", "CAMPAIGN_CREATION_FASTSTREAM", + "CAMPAIGN_CREATION_HAMLEYS", + "CAMPAIGN_CREATION_KONZUM", + "CAMPAIGN_CREATION_WEBSITEDEMOS", + "CAMPAIGN_CREATION_BBC", + "CAMPAIGN_CREATION_CINESTAR", + "CAMPAIGN_CREATION_FLOWERSHOP", + "CAMPAIGN_CREATION_GETBYBUS", ) CAMPAIGN_CREATION_IKEA = """Here is the customer brief: @@ -178,3 +185,370 @@ And the task is following: Create a new Google Ads campaign focusing on the 'Features' and 'Tutorial' pages of the FastStream website.""" + + +CAMPAIGN_CREATION_HAMLEYS = """Here is the customer brief: +Business: Boost sales / Increase brand awareness +Goal: Increase brand awareness and boost sales +Current Situation: Website: https://www.hamleys.com/, Digital Marketing: Yes, Using Google Ads +Website: https://www.hamleys.com/ +Digital Marketing Objectives: Increase brand awareness, Boost sales +Next Steps: First step is to get the summary of the Website. +Any Other Information Related to Customer Brief: None +Budget: recommended 3eur per day + +Focus Pages: +1. Construction Toys For Children | Hamleys: https://www.hamleys.com/shop-toys/construction +2. Children's Soft Toys | Plush Toys & Teddies | Hamleys: https://www.hamleys.com/shop-toys/soft-toys +3. PreSchool Children's Toys | Preschool | Hamleys: https://www.hamleys.com/shop-toys/preschool +4. Children's Action Toys & Toy Vehicles | Hamleys: https://www.hamleys.com/shop-toys/action-toys-vehicles +5. Children's Dolls & Fashion Toys | Hamleys: https://www.hamleys.com/shop-toys/dolls-fashion + +Additional info from the web page: +Here is a summary of the information you requested: + +Hamleys offers a wide range of children's toys including soft toys, LEGO & construction toys, preschool learning toys, action toys & vehicles, dolls & fashion toys, games & puzzles, and sports & leisure toys. The website features various categories to help customers find toys by price point and type. Unique selling points include a vast selection of high-quality toys from renowned brands and exclusive Hamleys soft toys. + +Relevant Pages: + +1. Construction Toys For Children | Hamleys: + URL: https://www.hamleys.com/shop-toys/construction + Summary: Product pages for construction toys + Keywords: 'LEGO Construction Toys', 'Playmobil Toys', 'Construction Toy Sets', 'Building Blocks', 'STEM Toys' + Headlines: 'Build Your Imagination', 'Explore {Keyword: LEGO Sets}', 'Creative Play with Playmobil', 'Top Construction Toy Sets', 'STEM Learning with Toys', 'Innovative Building Blocks', 'Fun with Construction Toys', 'Educational Building Sets', 'Play & Learn with LEGO', 'Discover Playmobil Fun', 'Best Construction Toys', 'Hands-On Learning Toys', 'Build & Create with Toys', 'Top-Rated Construction Sets', 'Engage with Building Toys' + Descriptions: 'Encourage creativity with LEGO sets.', 'Play and learn with Playmobil toys.', 'Top construction sets for kids.', 'STEM toys for hands-on learning.' + +2. Children's Soft Toys | Plush Toys & Teddies | Hamleys: + URL: https://www.hamleys.com/shop-toys/soft-toys + Summary: Product pages for soft toys + Keywords: 'Hamleys Soft Toys', 'Teddy Bears', 'Plush Figures', 'Animal Toys', 'Puppets' + Headlines: 'Cuddle with Hamleys Soft Toys', 'Adorable {Keyword: Teddy Bears}', 'Plush Figures for Kids', 'Animal Toys & Figures', 'Fun with Plush Puppets', 'Soft Toys for All Ages', 'Huggable Teddy Bears', 'Cute Plush Figures', 'Animal Friends for Kids', 'Interactive Plush Puppets', 'Best Soft Toys Collection', 'Comforting Soft Toys', 'Top-Rated Teddy Bears', 'Unique Plush Figures', 'Animal Toys for Imagination' + Descriptions: 'Discover Hamleys exclusive soft toys.', 'Cuddle with our adorable teddy bears.', 'Plush figures for endless fun.', 'Animal toys to spark imagination.' + +3. PreSchool Children's Toys | Preschool | Hamleys: + URL: https://www.hamleys.com/shop-toys/preschool + Summary: Product pages for preschool toys + Keywords: 'Bath Toys', 'Toys for Babies', 'Early Learning Toys', 'Educational Toys', 'Preschool Playsets' + Headlines: 'Fun {Keyword: Bath Toys}', 'Toys for Babies & Toddlers', 'Early Learning with Toys', 'Educational Preschool Toys', 'Interactive Bath Toys', 'Baby Toys for Development', 'Learning Through Play', 'Top Preschool Playsets', 'Engaging Early Learning Toys', 'Best Toys for Babies', 'Fun & Educational Toys', 'Preschool Learning Fun', 'Top-Rated Bath Toys', 'Baby Development Toys', 'Interactive Learning Toys' + Descriptions: 'Make bath time fun with bath toys.', "Toys for babies' development.", 'Early learning with educational toys.', 'Top preschool playsets for kids.' + +4. Children's Action Toys & Toy Vehicles | Hamleys: + URL: https://www.hamleys.com/shop-toys/action-toys-vehicles + Summary: Product pages for action toys and vehicles + Keywords: 'Action Figures', 'Toy Vehicles', 'Remote Control Toys', 'Robots', 'Vehicle Playsets' + Headlines: 'Exciting {Keyword: Action Figures}', 'Toy Vehicles for Kids', 'Remote Control Fun', 'Interactive Robots', 'Vehicle Playsets for Kids', 'Action Toys for Adventure', 'Top Toy Vehicles', 'Remote Control Cars', 'Fun with Action Figures', 'Best Robot Toys', 'Engaging Vehicle Playsets', 'Top-Rated Action Toys', 'Interactive Remote Control Toys', 'Exciting Robot Adventures', 'Vehicle Sets for Imagination' + Descriptions: 'Discover exciting action figures.', 'Toy vehicles for endless fun.', 'Remote control toys for kids.', 'Interactive robots for play.' + +5. Children's Dolls & Fashion Toys | Hamleys: + URL: https://www.hamleys.com/shop-toys/dolls-fashion + Summary: Product pages for dolls and fashion toys + Keywords: 'Fashion Dolls', 'Baby Dolls', 'Doll Accessories', 'Beauty Toys', 'Jewellery Toys' + Headlines: 'Stylish {Keyword: Fashion Dolls}', 'Adorable Baby Dolls', 'Doll Accessories for Fun', 'Beauty Toys for Kids', 'Jewellery Toys for Creativity', 'Fashion Dolls for Imagination', 'Top Baby Dolls', 'Fun Doll Accessories', 'Interactive Beauty Toys', 'Creative Jewellery Toys', 'Best Fashion Dolls', 'Engaging Baby Dolls', 'Top-Rated Doll Accessories', 'Fun with Beauty Toys', 'Creative Play with Jewellery' + Descriptions: 'Explore stylish fashion dolls.', 'Adorable baby dolls for kids.', 'Fun accessories for dolls.', 'Beauty toys for creative play.' + +6. Children's & Family Puzzle Games | Hamleys: + URL: https://www.hamleys.com/shop-toys/games-puzzles + Summary: Product pages for games and puzzles + Keywords: 'Board Games', 'Puzzles', 'Family Games', 'Educational Games', 'Strategy Games' + Headlines: 'Fun {Keyword: Board Games}', 'Challenging Puzzles', 'Family Games for All Ages', 'Educational Games for Kids', 'Strategy Games for Fun', 'Top Board Games', 'Engaging Puzzles', 'Family Fun with Games', 'Learning with Educational Games', 'Best Strategy Games', 'Top-Rated Board Games', 'Interactive Puzzles', 'Fun Family Games', 'Educational Play with Games', 'Challenging Strategy Games' + Descriptions: 'Discover fun board games.', 'Challenging puzzles for kids.', 'Family games for all ages.', 'Educational games for learning.' + +7. Children's Sports & Leisure Toys | Sports & Leisure Equipment | Hamleys: + URL: https://www.hamleys.com/shop-toys/sports-and-leisure + Summary: Product pages for sports and leisure toys + Keywords: 'Ride On Toys', 'Indoor Sports Toys', 'Outdoor Sports Toys', 'Sports Equipment', 'Leisure Playsets' + Headlines: 'Exciting {Keyword: Ride On Toys}', 'Indoor Sports Fun', 'Outdoor Sports Toys', 'Sports Equipment for Kids', 'Leisure Playsets for Fun', 'Top Ride On Toys', 'Engaging Indoor Sports Toys', 'Outdoor Fun with Sports Toys', 'Best Sports Equipment', 'Interactive Leisure Playsets', 'Top-Rated Ride On Toys', 'Fun Indoor Sports Toys', 'Outdoor Sports Adventures', 'Sports Equipment for Play', 'Creative Leisure Playsets' + Descriptions: 'Discover exciting ride on toys.', 'Indoor sports toys for fun.', 'Outdoor sports toys for kids.', 'Sports equipment for play.' + + + + +And the task is following: +Create a new Google Ads campaign""" + +CAMPAIGN_CREATION_KONZUM = """Here is the customer brief: +Business: Boost sales / Increase brand awareness +Goal: Increase brand awareness and boost sales +Current Situation: Website: https://www.konzum.hr, Digital Marketing: Yes, Using Google Ads +Website: https://www.konzum.hr +Digital Marketing Objectives: Increase brand awareness, Boost sales +Next Steps: First step is to get the summary of the Website. +Any Other Information Related to Customer Brief: None +Budget: 3eur per day +Focus Areas: Fresh Fruits and Vegetables, Dairy Products and Eggs + +Additional info from the web page: +Here is a summary of the information you requested: + +Page content: Konzum offers a wide range of products including fresh fruits and vegetables, dairy products, eggs, and various in-house brands. They also provide special offers and recipes. + +Relevant Pages: + +1. Voće i povrće: + URL: https://www.konzum.hr/web/t/kategorije/voce-i-povrce + Summary: Product pages for fruits and vegetables + Keywords: 'Fresh Fruits', 'Vegetables', 'Healthy Eating', 'Organic Produce', 'Local Produce' + Headlines: 'Fresh Fruits for You', 'Healthy Vegetables', 'Organic Produce Available', 'Local Fruits and Veggies', 'Seasonal Fruits', 'Fresh Vegetables Daily', 'Buy Fresh Fruits Online', 'Vegetables for Every Meal', 'Organic Fruits and Veggies', 'Local Produce Delivered', 'Fresh and Healthy Choices', 'Daily Fresh Vegetables', 'Seasonal Fresh Fruits', 'Healthy Organic Produce', 'Local Fresh Produce' + Descriptions: 'Get fresh fruits delivered to your door.', 'Healthy and fresh vegetables for every meal.', 'Organic produce available for a healthy lifestyle.', 'Local fruits and vegetables delivered fresh.' + +2. Mliječni proizvodi i jaja: + URL: https://www.konzum.hr/web/t/kategorije/mlijecni-proizvodi-i-jaja + Summary: Product pages for dairy products and eggs + Keywords: 'Dairy Products', 'Milk', 'Cheese', 'Eggs', 'Yogurt' + Headlines: 'Fresh Dairy Products', 'Quality Milk', 'Delicious Cheese', 'Fresh Eggs Daily', 'Yogurt and More', 'Buy Dairy Online', 'Fresh Milk Delivered', 'Cheese for Every Taste', 'Daily Fresh Eggs', 'Yogurt for Healthy Living', 'Quality Dairy Products', 'Fresh and Delicious Milk', 'Cheese Varieties', 'Healthy Fresh Eggs', 'Yogurt and Dairy Products' + Descriptions: 'Get fresh dairy products delivered to your door.', 'Quality milk for your daily needs.', 'Delicious cheese varieties available.', 'Fresh eggs delivered daily.' + +3. Smrznuto voće i povrće: + URL: https://www.konzum.hr/web/t/kategorije/voce-i-povrce/smrznuto-voce-i-povrce + Summary: Product pages for frozen fruits and vegetables + Keywords: 'Frozen Fruits', 'Frozen Vegetables', 'Convenient Cooking', 'Healthy Frozen Food', 'Quick Meals' + Headlines: 'Frozen Fruits for You', 'Healthy Frozen Vegetables', 'Convenient Frozen Food', 'Quick and Easy Meals', 'Frozen Fruits Delivered', 'Healthy Frozen Choices', 'Buy Frozen Vegetables', 'Frozen Fruits for Smoothies', 'Quick Frozen Meals', 'Healthy Frozen Options', 'Frozen Fruits and Veggies', 'Convenient Frozen Meals', 'Healthy Frozen Produce', 'Quick Frozen Vegetables', 'Frozen Fruits for Healthy Living' + Descriptions: 'Get frozen fruits delivered to your door.', 'Healthy and convenient frozen vegetables.', 'Quick and easy frozen meals.', 'Frozen fruits and vegetables for healthy living.' + + + + +And the task is following: +Create new Google Ads campaign""" + +CAMPAIGN_CREATION_WEBSITEDEMOS = """Here is the customer brief: +Business: Boost sales / Increase brand awareness +Goal: Increase brand awareness and boost sales +Current Situation: Website: https://websitedemos.net/organic-shop-02/, Digital Marketing: Yes, Using Google Ads +Website: https://websitedemos.net/organic-shop-02/ +Digital Marketing Objectives: Increase brand awareness, Boost sales +Next Steps: First step is to get the summary of the Website. +Any Other Information Related to Customer Brief: None +Budget: 3 EUR per day + +Additional info from the web page: +Here is a summary of the information you requested: + +The Organic Store website offers a variety of organic products including groceries and juices. The store emphasizes quality with features like free shipping, certified organic products, huge savings, and easy returns. Popular products include assorted coffee, hand sanitizer, handpicked red chillies, natural extracted olive oil, and fresh orange juice. + +Relevant Pages: + +1. Shop - Organic Store: + URL: https://websitedemos.net/organic-shop-02/shop/ + Summary: Product pages for all items + Keywords: 'Organic Products', 'Groceries', 'Juices', 'Free Shipping', 'Certified Organic', 'Huge Savings' + Headlines: 'Shop the Best Organic Products', 'Discover Our Organic Selection', 'Certified Organic Products', 'Huge Savings on Organic Items', 'Free Shipping on Orders Over $5', 'Easy Returns on All Products', 'Join the Organic Movement', 'Shop Now for Organic Groceries', 'Fresh Organic Juices Available', 'Lowest Prices on Organic Goods', 'Top Quality Organic Products', 'Organic Groceries for Your Home', 'Healthy and Organic Choices', 'Save Big on Organic Products', '{Keyword: Organic Products}' + Descriptions: 'Explore our wide range of organic products.', 'Certified organic items with free shipping.', 'Huge savings on top-quality organic goods.', 'Easy returns on all organic products.' + +2. Groceries Archives - Organic Store: + URL: https://websitedemos.net/organic-shop-02/product-category/groceries/ + Summary: Product pages for groceries + Keywords: 'Organic Groceries', 'Healthy Food', 'Natural Products', 'Certified Organic', 'Free Shipping', 'Huge Savings' + Headlines: 'Shop Organic Groceries Now', 'Healthy Organic Groceries', 'Certified Organic Groceries', 'Free Shipping on Groceries', 'Huge Savings on Groceries', 'Top Quality Organic Groceries', 'Fresh and Natural Groceries', 'Organic Groceries for Your Home', 'Best Prices on Organic Groceries', 'Join the Organic Grocery Movement', 'Easy Returns on Groceries', 'Shop Now for Organic Groceries', 'Healthy Choices for Your Family', 'Save Big on Organic Groceries', '{Keyword: Organic Groceries}' + Descriptions: 'Discover our range of organic groceries.', 'Certified organic groceries with free shipping.', 'Huge savings on top-quality groceries.', 'Easy returns on all grocery items.' + +3. Juice Archives - Organic Store: + URL: https://websitedemos.net/organic-shop-02/product-category/juice/ + Summary: Product pages for juices + Keywords: 'Organic Juices', 'Healthy Drinks', 'Natural Juices', 'Certified Organic', 'Free Shipping', 'Huge Savings' + Headlines: 'Shop Organic Juices Now', 'Healthy Organic Juices', 'Certified Organic Juices', 'Free Shipping on Juices', 'Huge Savings on Juices', 'Top Quality Organic Juices', 'Fresh and Natural Juices', 'Organic Juices for Your Home', 'Best Prices on Organic Juices', 'Join the Organic Juice Movement', 'Easy Returns on Juices', 'Shop Now for Organic Juices', 'Healthy Drinks for Your Family', 'Save Big on Organic Juices', '{Keyword: Organic Juices}' + Descriptions: 'Discover our range of organic juices.', 'Certified organic juices with free shipping.', 'Huge savings on top-quality juices.', 'Easy returns on all juice products.' + + + + +And the task is following: +Create a new Google Ads campaign for the client.""" + +CAMPAIGN_CREATION_BBC = """Here is the customer brief: +Business: Boost sales / Increase brand awareness +Goal: Increase brand awareness and boost sales +Current Situation: Website: www.bbc.com/news, Digital Marketing: Yes, Using Google Ads +Website: www.bbc.com/news +Digital Marketing Objectives: Increase brand awareness, Boost sales +Next Steps: First step is to get the summary of the Website. +Any Other Information Related to Customer Brief: None +Budget: 3eur per day + +Additional info from the web page: +Here is a summary of the information you requested: + +Page content: BBC Sport offers comprehensive coverage of various sports including football, cricket, Formula 1, rugby, tennis, golf, athletics, and cycling. The website provides live scores, fixtures, results, and video highlights. It also features news articles, player profiles, and in-depth analysis. Unique selling points include real-time updates, extensive coverage of major sports events, and a user-friendly interface. + +Relevant Pages: + +1. Football: + URL: https://www.bbc.com/sport/football + Summary: Latest news, scores, fixtures, and video highlights for football. + Keywords: 'Football', 'Live Scores', 'Fixtures', 'Results', 'Video Highlights', 'Premier League', 'UEFA', 'Champions League', 'Transfers', 'Top Scorers', "Women's Football", 'European Football', 'Teams', 'Leagues', 'Cups' + Headlines: 'Live Football Scores & Updates', 'Latest Football News Today', 'Football Fixtures & Results', 'Watch Football Video Highlights', 'Premier League News & Updates', 'UEFA Champions League News', 'Football Transfer News', 'Top Scorers in Football', "Women's Football News", 'European Football Updates', 'All Football Teams & Leagues', 'Football Leagues & Cups', 'Football Gossip & Rumors', 'Football Match Previews', '{Keyword: Football News}' + Descriptions: 'Get live football scores and updates.', 'Read the latest football news today.', 'Check football fixtures and results.', 'Watch video highlights of football matches.' + +2. UEFA Euro 2024: + URL: https://www.bbc.com/sport/football/european-championship + Summary: News, qualifiers, scores, and fixtures for UEFA Euro 2024. + Keywords: 'UEFA Euro 2024', 'Euro 2024 News', 'Euro 2024 Qualifiers', 'Euro 2024 Scores', 'Euro 2024 Fixtures', 'Euro 2024 Results', 'Euro 2024 Teams', 'Euro 2024 Groups', 'Euro 2024 Tables', 'Euro 2024 Highlights', 'Euro 2024 Matches', 'Euro 2024 Schedule', 'Euro 2024 Updates', 'Euro 2024 Live', 'Euro 2024 Coverage' + Headlines: 'UEFA Euro 2024 News & Updates', 'Euro 2024 Qualifiers & Results', 'Live Scores for Euro 2024', 'Euro 2024 Fixtures & Schedule', 'Euro 2024 Teams & Groups', 'Euro 2024 Tables & Standings', 'Watch Euro 2024 Highlights', 'Euro 2024 Match Previews', 'Euro 2024 Live Coverage', 'Latest Euro 2024 News', 'Euro 2024 Player Profiles', 'Euro 2024 Match Analysis', 'Euro 2024 Tournament Updates', 'Euro 2024 Fan Reactions', '{Keyword: Euro 2024 News}' + Descriptions: 'Get the latest news and updates on UEFA Euro 2024.', 'Check Euro 2024 qualifiers and results.', 'Find live scores for Euro 2024 matches.', 'View fixtures and schedule for Euro 2024.' + +3. UEFA Euro 2024 Scores & Fixtures: + URL: https://www.bbc.com/sport/football/european-championship/scores-fixtures + Summary: Scores and fixtures for UEFA Euro 2024. + Keywords: 'Euro 2024 Scores', 'Euro 2024 Fixtures', 'Euro 2024 Schedule', 'Euro 2024 Matches', 'Euro 2024 Results', 'Euro 2024 Live Scores', 'Euro 2024 Updates', 'Euro 2024 Calendar', 'Euro 2024 Match Dates', 'Euro 2024 Game Times', 'Euro 2024 Match Schedule', 'Euro 2024 Fixtures List', 'Euro 2024 Match Fixtures', 'Euro 2024 Live Updates', 'Euro 2024 Match Results' + Headlines: 'Euro 2024 Scores & Fixtures', 'Live Scores for Euro 2024', 'Euro 2024 Match Schedule', 'Euro 2024 Fixtures List', 'Euro 2024 Game Times', 'Euro 2024 Match Dates', 'Euro 2024 Live Updates', 'Euro 2024 Match Results', 'Euro 2024 Calendar', 'Euro 2024 Match Fixtures', 'Euro 2024 Fixtures & Results', 'Euro 2024 Live Match Scores', 'Euro 2024 Match Times', 'Euro 2024 Schedule & Updates', '{Keyword: Euro 2024 Scores}' + Descriptions: 'Find scores and fixtures for UEFA Euro 2024.', 'Get live scores for Euro 2024 matches.', 'Check the match schedule for Euro 2024.', 'View the fixtures list for Euro 2024.' + + + + +And the task is following: +Create a new Google Ads campaign""" + +CAMPAIGN_CREATION_CINESTAR = """Here is the customer brief: +Business: Boost sales / Increase brand awareness +Goal: Increase brand awareness and boost sales +Current Situation: Website: https://zagreb.cinestarcinemas.hr/, Digital Marketing: Yes, Using Google Ads +Website: https://zagreb.cinestarcinemas.hr/ +Digital Marketing Objectives: Increase brand awareness, Boost sales +Next Steps: First step is to get the summary of the Website. +Any Other Information Related to Customer Brief: None +Budget: 3eur per day + +Relevant Pages: +1. Dječji Rođendani: Birthday party packages for children +2. Školske Projekcije: School screenings with discounts + +Additional info from the web page: +Here is a summary of the information you requested: + +CineStar Cinemas in Zagreb offers a variety of services including birthday party packages, school screenings, and online ticket purchasing. They provide different birthday packages with options for 2D and 4DX screenings, professional animators, and various menu choices. School screenings offer discounted tickets and menus for students, with free tickets and popcorn for teachers. The e-payment system allows for easy online ticket purchases with secure data handling. + +Relevant Pages: + +1. Dječji Rođendani: + URL: https://zagreb.cinestarcinemas.hr/djeca-i-obitelj/djecji-rodendani + Summary: Birthday party packages for children + Keywords: 'Birthday Parties', 'Kids Parties', 'CineStar Birthday', 'Birthday Packages', '4DX Birthday' + Headlines: 'Celebrate with {Keyword: CineStar}', 'Total Cool Birthday Party', 'Choose Your Birthday Package', 'Basic Birthday Package', 'Party in the Birthday Room', '4DX Birthday Package', 'Kids Hall Party', 'Mini Birthday Package', 'Cool Birthday Package', 'Movie Birthday Package', 'Professional Animator Service', 'Add 4DX Fun to Your Party', 'Add eXtreme Fun to Your Party', 'Add 3D Fun to Your Party', 'Add ScreenX Fun to Your Party' + Descriptions: 'Celebrate your birthday with a movie, popcorn, and friends at CineStar.', 'Choose from various birthday packages including 2D and 4DX screenings.', 'Add professional animators to make your party even more fun.', 'Enjoy special birthday menus and gifts for the birthday child.' + +2. Školske Projekcije: + URL: https://zagreb.cinestarcinemas.hr/djeca-i-obitelj/skolske-projekcije + Summary: School screenings with discounts + Keywords: 'School Screenings', 'Student Discounts', 'CineStar School', 'Educational Screenings', 'Group Discounts' + Headlines: 'School Screenings at CineStar', 'Discounted Tickets for Students', 'Free Tickets for Teachers', 'Enjoy Movies with Your Class', 'CinesCool Day', 'Organize a School Screening', 'Special Prices for Schools', 'Educational Movie Experience', 'Combine Fun and Learning', 'Group Discounts Available', 'Special Menus for Students', 'Free Popcorn for Teachers', 'Book Your School Screening', 'Enjoy IMAX Documentaries', 'Plan Your School Trip' + Descriptions: 'Organize a school trip to CineStar with discounted tickets and menus.', 'Teachers get free tickets and popcorn with school screenings.', 'Enjoy educational movies and special group discounts.', 'Book your school screening and enjoy a fun learning experience.' + +3. e-plaćanje: + URL: https://zagreb.cinestarcinemas.hr/e-placanje + Summary: Online ticket purchasing + Keywords: 'Online Ticket Purchase', 'e-Payment', 'CineStar Tickets', 'Secure Payment', 'Buy Tickets Online' + Headlines: 'Buy Tickets Online', 'Easy Online Ticket Purchase', 'Secure e-Payment System', 'Purchase Tickets from Home', 'Fast and Easy Ticket Buying', 'Enjoy Movies with e-Payment', 'Safe Online Transactions', 'Corvus Pay for Secure Payment', 'No Data Storage on Server', 'Register for Online Purchase', 'Secure Your Account', 'PIN Protection for Cards', 'Follow Security Guidelines', 'Enjoy Movies with Ease', 'Book Your Tickets Online' + Descriptions: 'Buy your CineStar tickets online quickly and securely.', 'Enjoy the convenience of e-payment for movie tickets.', 'Secure transactions with Corvus Pay system.', 'Register and follow security guidelines for safe purchases.' + + + + +And the task is following: +Create a new Google Ads campaign""" + +CAMPAIGN_CREATION_FLOWERSHOP = """Here is the customer brief: +Business: Boost sales / Increase brand awareness +Goal: Increase brand awareness and boost sales +Current Situation: Website: https://camelbackflowershop.com/, Digital Marketing: Yes, Using Google Ads +Website: https://camelbackflowershop.com/ +Digital Marketing Objectives: Increase brand awareness, Boost sales +Next Steps: First step is to get the summary of the Website. +Any Other Information Related to Customer Brief: None +Budget: (recommended 3eur per day) + +Relevant Pages: +1. Wine & Flowers: Combination of wine and flowers. [Link](https://camelbackflowershop.com/collections/wine) +2. Gift Boxes: Variety of gift boxes. [Link](https://camelbackflowershop.com/collections/gift-box-collection) + +Additional info from the web page: +Here is a summary of the information you requested: + +Camelback Flowershop offers a variety of products including flowers, wine, gift boxes, and plants. They provide same-day delivery for orders placed before 2 PM. Their unique selling points include designer's choice floral arrangements, wine and flower combinations, and a wide range of gift boxes for different occasions. + +Relevant Pages: + +1. Wine & Flowers: + URL: https://camelbackflowershop.com/collections/wine + Summary: Combination of wine and flowers + Keywords: 'Wine & Flowers', 'Gift Sets', 'Same-Day Delivery', 'Phoenix', 'Luxury Gifts' + Headlines: 'Elegant Wine & Flower Sets', 'Same-Day {Keyword:Delivery}', 'Luxury Wine & Flower Gifts', 'Perfect for Any Occasion', 'Wine & Flowers in Phoenix', 'Unique Gift Combinations', 'Order Wine & Flowers Today', 'Premium Wine & Floral Sets', 'Gift Wine & Flowers Now', 'Wine & Flowers Delivered', 'Exclusive Wine & Flowers', 'Wine & Flowers for Events', 'Best Wine & Flower Gifts', 'Wine & Flowers for Romance', 'Wine & Flowers for Sympathy' + Descriptions: 'Elegant wine and flower sets for any occasion.', 'Same-day delivery available in Phoenix.', 'Luxury gifts combining wine and flowers.', 'Perfect for romantic or sympathy gestures.' + +2. Gift Boxes: + URL: https://camelbackflowershop.com/collections/gift-box-collection + Summary: Variety of gift boxes + Keywords: 'Gift Boxes', 'Luxury Gifts', 'Same-Day Delivery', 'Phoenix', 'Special Occasions' + Headlines: 'Luxury Gift Boxes', 'Same-Day {Keyword:Delivery}', 'Gift Boxes for All Occasions', 'Unique Gift Box Sets', 'Gift Boxes in Phoenix', 'Order Gift Boxes Today', 'Premium Gift Box Collection', 'Exclusive Gift Boxes', 'Gift Boxes for Special Events', 'Best Gift Box Sets', 'Gift Boxes for Romance', 'Gift Boxes for Sympathy', 'Gift Boxes for Birthdays', 'Gift Boxes for Anniversaries', 'Gift Boxes for Holidays' + Descriptions: 'Luxury gift boxes for all occasions.', 'Same-day delivery available in Phoenix.', 'Unique gift box sets for special events.', 'Perfect for birthdays, anniversaries, and holidays.' + +3. Plants: + URL: https://camelbackflowershop.com/collections/all-plants + Summary: Variety of plants + Keywords: 'Plants', 'Succulents', 'Cacti', 'Orchids', 'Same-Day Delivery', 'Phoenix' + Headlines: 'Beautiful Plants', 'Same-Day {Keyword:Delivery}', 'Succulents & Cacti', 'Orchids & More', 'Plants in Phoenix', 'Order Plants Today', 'Premium Plant Collection', 'Exclusive Plant Varieties', 'Plants for Home & Office', 'Best Plant Selection', 'Plants for Gifts', 'Plants for Decor', 'Plants for Events', 'Plants for Sympathy', 'Plants for Romance' + Descriptions: 'Beautiful plants for home and office.', 'Same-day delivery available in Phoenix.', 'Wide variety of succulents, cacti, and orchids.', 'Perfect for gifts, decor, and events.' + + + + +And the task is following: +Create a new Google Ads campaign""" + +CAMPAIGN_CREATION_GETBYBUS = """Here is the customer brief: +Business: Boost sales / Increase brand awareness +Goal: Increase brand awareness and boost sales +Current Situation: Website: https://getbybus.com/hr/, Digital Marketing: Yes, Using Google Ads +Website: https://getbybus.com/hr/ +Digital Marketing Objectives: Increase brand awareness, Boost sales +Next Steps: First step is to get the summary of the Website. +Any Other Information Related to Customer Brief: None +Budget: 3 EUR per day + +Additional info from the web page: +Here is a summary of the information you requested: + +GetByBus is a platform that simplifies bus travel by connecting 198,525 stations. It offers services such as finding bus stations, purchasing one-way and return tickets, and ensuring luggage safety during travel. The website provides detailed guides and blog posts to assist travelers. + +Relevant Pages: + +1. Pronađite autobusne kolodvore i stanice na GetByBus.com: + URL: https://getbybus.com/hr/station-locator + Summary: Locator for bus stations in various countries. + Keywords: 'Bus Stations', 'Travel', 'Locator', 'GetByBus', 'Bus Stops', 'Station Finder' + Headlines: 'Find Bus Stations Easily', 'Locate Bus Stops Quickly', 'Bus Stations Near You', 'Find {Keyword:Bus Stations}', 'Bus Station Locator', 'Search Bus Stations', 'Find Bus Stops', 'Locate {Keyword:Bus Stops}', 'Bus Stations Worldwide', 'Find Bus Stations Fast', 'Bus Station Finder', 'Locate Bus Stations', 'Find Bus Stops Easily', 'Search {Keyword:Bus Stops}', 'Bus Station Search' + Descriptions: 'Easily find bus stations near you.', 'Quickly locate bus stops worldwide.', 'Search for bus stations in various countries.', 'Find bus stops and stations easily.' + +2. Autobusne Stanice Hrvatska - Lista svih kolodvora: + URL: https://getbybus.com/hr/drzava/hrvatska/autobusne-stanice + Summary: List of all bus stations in Croatia. + Keywords: 'Croatia Bus Stations', 'Bus Stops Croatia', 'GetByBus Croatia', 'Bus Stations List', 'Croatia Travel' + Headlines: 'Croatia Bus Stations List', 'Find Bus Stations in Croatia', 'Croatia {Keyword:Bus Stations}', 'Bus Stops in Croatia', 'Locate Croatia Bus Stops', 'Find {Keyword:Bus Stops} in Croatia', 'Croatia Bus Station Finder', 'Search Bus Stations in Croatia', 'Croatia Bus Stops Locator', 'Find Bus Stations in {Keyword:Croatia}', 'Croatia Bus Stations Search', 'Locate Bus Stations in Croatia', 'Find Bus Stops in Croatia', 'Search {Keyword:Bus Stations} in Croatia', 'Croatia Bus Station Search' + Descriptions: 'Find all bus stations in Croatia.', 'Locate bus stops in Croatia easily.', 'Search for bus stations in Croatia.', 'Find bus stops and stations in Croatia.' + +3. Kupovina jednosmjerne autobusne karte na GetByBus-u - GetByBus Blog: + URL: https://getbybus.com/hr/blog/kupovina-jednosmjerne-autobusne-karte-na-getbybus-u/ + Summary: Guide on purchasing one-way bus tickets. + Keywords: 'One-Way Bus Tickets', 'GetByBus Tickets', 'Bus Travel', 'Ticket Purchase Guide', 'Bus Tickets' + Headlines: 'Buy One-Way Bus Tickets', 'Purchase {Keyword:Bus Tickets}', 'One-Way Tickets on GetByBus', 'GetByBus Ticket Guide', 'How to Buy Bus Tickets', 'One-Way Bus Ticket Purchase', 'Get {Keyword:Bus Tickets}', 'Buy Bus Tickets Easily', 'Purchase One-Way Tickets', 'GetByBus One-Way Tickets', 'Buy {Keyword:One-Way Tickets}', 'Bus Ticket Purchase Guide', 'Get Your Bus Tickets', 'Buy Tickets on GetByBus', 'One-Way Ticket Guide' + Descriptions: 'Guide to buying one-way bus tickets.', 'Purchase one-way bus tickets easily.', 'How to buy one-way bus tickets.', 'Get one-way bus tickets on GetByBus.' + +4. Kupovina povratne karte - GetByBus Blog: + URL: https://getbybus.com/hr/blog/kupovina-povratne-karte/ + Summary: Guide on purchasing return bus tickets. + Keywords: 'Return Bus Tickets', 'GetByBus Tickets', 'Bus Travel', 'Ticket Purchase Guide', 'Bus Tickets' + Headlines: 'Buy Return Bus Tickets', 'Purchase {Keyword:Bus Tickets}', 'Return Tickets on GetByBus', 'GetByBus Ticket Guide', 'How to Buy Bus Tickets', 'Return Bus Ticket Purchase', 'Get {Keyword:Bus Tickets}', 'Buy Bus Tickets Easily', 'Purchase Return Tickets', 'GetByBus Return Tickets', 'Buy {Keyword:Return Tickets}', 'Bus Ticket Purchase Guide', 'Get Your Bus Tickets', 'Buy Tickets on GetByBus', 'Return Ticket Guide' + Descriptions: 'Guide to buying return bus tickets.', 'Purchase return bus tickets easily.', 'How to buy return bus tickets.', 'Get return bus tickets on GetByBus.' + +5. Sigurnost prtljage tijekom putovanja autobusom - GetByBus Blog: + URL: https://getbybus.com/hr/blog/putovanje-autobusom-sa-prtljagom-u-inozemstvu/ + Summary: Guide on luggage safety during bus travel. + Keywords: 'Luggage Safety', 'Bus Travel', 'GetByBus Guide', 'Travel Tips', 'Bus Luggage' + Headlines: 'Luggage Safety Tips', 'Bus Travel {Keyword:Safety}', 'Keep Luggage Safe', 'GetByBus Luggage Guide', 'Luggage Safety on Buses', 'Travel with Safe Luggage', 'Bus Luggage Safety Tips', 'Keep {Keyword:Luggage Safe}', 'Safe Luggage Travel', 'Luggage Safety Guide', 'Bus Travel Tips', 'Safe Travel with Luggage', 'GetByBus Travel Guide', 'Luggage Safety Tips', 'Travel {Keyword:Safety} Tips' + Descriptions: 'Guide to luggage safety during bus travel.', 'Keep your luggage safe on buses.', 'Tips for safe luggage travel.', 'Ensure luggage safety during bus trips.' + + + + +And the task is following: +Create a new Google Ads campaign for GetByBus to increase brand awareness and boost sales.""" diff --git a/scripts/benchmark.sh b/scripts/benchmark.sh index ea3524fb..d3370ae6 100755 --- a/scripts/benchmark.sh +++ b/scripts/benchmark.sh @@ -14,38 +14,47 @@ while getopts ":t:" opt; do esac done +# if team name is 'all' , create teams_list equal to avaliable_teams +if [ "$team_name" == "all" ]; then + teams_list=("${avaliable_teams[@]}") + echo "Benchmarking all teams: ${teams_list[@]}" # check if the team name is valid -if [[ ! " ${avaliable_teams[@]} " =~ " ${team_name} " ]]; then +elif [[ ! " ${avaliable_teams[@]} " =~ " ${team_name} " ]]; then echo "Invalid team name: $team_name" echo "Available team names: ${avaliable_teams[@]}" exit 1 +else + teams_list=("$team_name") + echo "Benchmarking team: $team_name" fi -echo "Team name: $team_name" - -start=`date +%s` - date=$(date +"%FT%T") -output_dir="benchmarking/working" -file_name="$team_name-benchmark-task-list-$date.csv" - -echo "Output directory: $output_dir" -echo "File name: $file_name" - -# Generate the task table -if [ "$team_name" == "brief-creation" ]; then - benchmark generate-task-table-for-brief-creation --output-dir $output_dir --file-name $file_name -elif [ "$team_name" == "campaign-creation" ]; then - benchmark generate-task-table-for-campaign-creation --output-dir $output_dir --file-name $file_name -elif [ "$team_name" == "end2end" ]; then - benchmark generate-task-table-for-campaign-creation --output-dir $output_dir --file-name $file_name --end2end -elif [ "$team_name" == "websurfer" ]; then - benchmark generate-task-table-for-websurfer --output-dir $output_dir --file-name $file_name -fi - -echo "File path: $output_dir/$file_name" -mkdir -p "$output_dir/logs" -benchmark run-tests --file-path "$output_dir/$file_name" > "$output_dir/logs/$team_name-benchmark-result-$date.txt" - -end=`date +%s` -echo Total execution time: $((end-start))s +for team_name in "${teams_list[@]}"; do + echo "Team name: $team_name" + + start=`date +%s` + + output_dir="benchmarking/working/$date" + file_name="$team_name-benchmark-task-list.csv" + + echo "Output directory: $output_dir" + echo "File name: $file_name" + + # Generate the task table + if [ "$team_name" == "brief-creation" ]; then + benchmark generate-task-table-for-brief-creation --output-dir $output_dir --file-name $file_name + elif [ "$team_name" == "campaign-creation" ]; then + benchmark generate-task-table-for-campaign-creation --output-dir $output_dir --file-name $file_name + elif [ "$team_name" == "end2end" ]; then + benchmark generate-task-table-for-campaign-creation --output-dir $output_dir --file-name $file_name --end2end + elif [ "$team_name" == "websurfer" ]; then + benchmark generate-task-table-for-websurfer --output-dir $output_dir --file-name $file_name + fi + + echo "File path: $output_dir/$file_name" + mkdir -p "$output_dir/logs" + benchmark run-tests --file-path "$output_dir/$file_name" > "$output_dir/logs/$team_name-benchmark-result.txt" + + end=`date +%s` + echo Total execution time: $((end-start))s +done diff --git a/tests/ci/captn/captn_agents/backend/benchmarking/test_benchmarking.py b/tests/ci/captn/captn_agents/backend/benchmarking/test_benchmarking.py index 17c3045f..7da169d6 100644 --- a/tests/ci/captn/captn_agents/backend/benchmarking/test_benchmarking.py +++ b/tests/ci/captn/captn_agents/backend/benchmarking/test_benchmarking.py @@ -254,7 +254,7 @@ def test_generate_task_table_for_campaign_creation_success(self): command=self.command, file_name=self.file_name, tmp_dir=tmp_dir, - no_rows=30, + no_rows=50, ) @pytest.mark.parametrize("end2end_param", ["--end2end"]) # , "--no-end2end"]) @@ -280,6 +280,6 @@ def test_run_tests_for_campaign_creation_success( file_name=self.file_name, aggregated_csv_name=self.aggregated_csv_name, success=success, - no_rows=30, + no_rows=50, additional_generate_task_table_parameters=[end2end_param], ) From cfac5d61f439144e3e3b6c492ba0e7b8f4875d7d Mon Sep 17 00:00:00 2001 From: rjambrecic <32619626+rjambrecic@users.noreply.github.com> Date: Fri, 7 Jun 2024 08:38:40 +0200 Subject: [PATCH 4/4] 693 use cache for the get info from the web page function (#750) * Add cache to the get_info_from_the_web_page function * Clear cache of the get_info_from_webpage for each end2end test * Fix tests * Fix tests --- .../benchmarking/brief_creation_team.py | 125 +++++++++--------- .../backend/benchmarking/end2end.py | 4 +- .../tools/_brief_creation_team_tools.py | 10 +- .../captn_agents/backend/tools/_functions.py | 2 + .../backend/tools/test_functions.py | 26 ++++ 5 files changed, 102 insertions(+), 65 deletions(-) diff --git a/captn/captn_agents/backend/benchmarking/brief_creation_team.py b/captn/captn_agents/backend/benchmarking/brief_creation_team.py index 9be66e4f..33c7ad74 100644 --- a/captn/captn_agents/backend/benchmarking/brief_creation_team.py +++ b/captn/captn_agents/backend/benchmarking/brief_creation_team.py @@ -1,7 +1,7 @@ from contextlib import contextmanager from tempfile import TemporaryDirectory from typing import Any, Iterator, Tuple -from unittest.mock import patch +from unittest.mock import MagicMock, patch from autogen.cache import Cache @@ -47,11 +47,10 @@ @contextmanager def _patch_vars( - url: str, team: BriefCreationTeam, client_system_message: str, cache: Cache, -) -> Iterator[Tuple[Any, Any, Any, Any]]: +) -> Iterator[Tuple[Any, Any, Any]]: with ( patch.object( team.toolbox.functions, @@ -63,10 +62,6 @@ def _patch_vars( client_system_message=client_system_message, ), ) as mock_reply_to_client, - patch( - "captn.captn_agents.backend.tools._brief_creation_team_tools._get_info_from_the_web_page_original", - return_value=URL_SUMMARY_DICT[url], - ) as mock_get_info_from_the_web_page, patch( "captn.captn_agents.backend.tools._brief_creation_team_tools._change_the_team_and_start_new_chat", return_value=BRIEF_CREATION_TEAM_RESPONSE, @@ -79,7 +74,6 @@ def _patch_vars( ): yield ( mock_reply_to_client, - mock_get_info_from_the_web_page, mock_change_the_team_and_start_new_chat, mock_get_brief_template, ) @@ -129,56 +123,65 @@ def benchmark_brief_creation( user_id = 123 conv_id = 234 task = _get_task(url) - team = BriefCreationTeam( - task=task, user_id=user_id, conv_id=conv_id, config_list=config_list - ) - client_system_message = _client_system_messages[team_name] - try: - with TemporaryDirectory() as cache_dir: - with Cache.disk(cache_path_root=cache_dir) as cache: - with _patch_vars( - url=url, - team=team, - client_system_message=client_system_message, - cache=cache, - ) as ( - _, - mock_get_info_from_the_web_page, - mock_change_the_team_and_start_new_chat, - mock_get_brief_template, - ): - # return "it's ok" - team.initiate_chat(cache=cache) - - mock_get_info_from_the_web_page.assert_called() - mock_get_brief_template.assert_called() - mock_change_the_team_and_start_new_chat.assert_called() - team_class: Team = ( - mock_change_the_team_and_start_new_chat.call_args.kwargs[ - "team_class" - ] - ) - assert team_class.get_registred_team_name() == team_name # nosec: [B101] - - delegate_task_function_sugestion = team.get_messages()[-2] - assert "tool_calls" in delegate_task_function_sugestion # nosec: [B101] - - delegate_task_function_sugestion_function = ( - delegate_task_function_sugestion["tool_calls"][0]["function"] - ) - assert ( - delegate_task_function_sugestion_function["name"] - == "delagate_task" - ) # nosec: [B101] - - assert "arguments" in delegate_task_function_sugestion_function # nosec: [B101] - assert ( - "task" in delegate_task_function_sugestion_function["arguments"] - ) # nosec: [B101] - - return delegate_task_function_sugestion_function[ - "arguments" - ], team.retry_from_scratch_counter - finally: - poped_team = Team.pop_team(user_id=user_id, conv_id=conv_id) - assert isinstance(poped_team, Team) # nosec: [B101] + + with patch( + "captn.captn_agents.backend.tools._brief_creation_team_tools.WebPageInfo.get_info_from_the_web_page_f", + ) as mock_get_info_from_the_web_page: + f = MagicMock() + f.return_value = URL_SUMMARY_DICT[url] + mock_get_info_from_the_web_page.return_value = f + + team = BriefCreationTeam( + task=task, user_id=user_id, conv_id=conv_id, config_list=config_list + ) + client_system_message = _client_system_messages[team_name] + try: + with TemporaryDirectory() as cache_dir: + with Cache.disk(cache_path_root=cache_dir) as cache: + with _patch_vars( + team=team, + client_system_message=client_system_message, + cache=cache, + ) as ( + _, + mock_change_the_team_and_start_new_chat, + mock_get_brief_template, + ): + # return "it's ok" + team.initiate_chat(cache=cache) + + mock_get_info_from_the_web_page.assert_called() + mock_get_brief_template.assert_called() + mock_change_the_team_and_start_new_chat.assert_called() + team_class: Team = ( + mock_change_the_team_and_start_new_chat.call_args.kwargs[ + "team_class" + ] + ) + assert team_class.get_registred_team_name() == team_name # nosec: [B101] + + delegate_task_function_sugestion = team.get_messages()[-2] + assert "tool_calls" in delegate_task_function_sugestion # nosec: [B101] + + delegate_task_function_sugestion_function = ( + delegate_task_function_sugestion["tool_calls"][0][ + "function" + ] + ) + assert ( + delegate_task_function_sugestion_function["name"] + == "delagate_task" + ) # nosec: [B101] + + assert "arguments" in delegate_task_function_sugestion_function # nosec: [B101] + assert ( + "task" + in delegate_task_function_sugestion_function["arguments"] + ) # nosec: [B101] + + return delegate_task_function_sugestion_function[ + "arguments" + ], team.retry_from_scratch_counter + finally: + poped_team = Team.pop_team(user_id=user_id, conv_id=conv_id) + assert isinstance(poped_team, Team) # nosec: [B101] diff --git a/captn/captn_agents/backend/benchmarking/end2end.py b/captn/captn_agents/backend/benchmarking/end2end.py index a6d0ceff..44b1ba8f 100644 --- a/captn/captn_agents/backend/benchmarking/end2end.py +++ b/captn/captn_agents/backend/benchmarking/end2end.py @@ -10,7 +10,9 @@ CampaignCreationTeam, Team, ) -from ..tools._brief_creation_team_tools import _change_the_team_and_start_new_chat +from ..tools._brief_creation_team_tools import ( + _change_the_team_and_start_new_chat, +) from .brief_creation_team import _client_system_messages, _get_task from .campaign_creation_team import ( _patch_campaign_creation_team_vars, diff --git a/captn/captn_agents/backend/tools/_brief_creation_team_tools.py b/captn/captn_agents/backend/tools/_brief_creation_team_tools.py index 96724248..6ef9af77 100644 --- a/captn/captn_agents/backend/tools/_brief_creation_team_tools.py +++ b/captn/captn_agents/backend/tools/_brief_creation_team_tools.py @@ -1,5 +1,5 @@ from dataclasses import dataclass, field -from typing import Dict, Type +from typing import Callable, Dict, Type from pydantic import BaseModel, Field from typing_extensions import Annotated @@ -38,7 +38,9 @@ class DelegateTask(BaseModel): ] -_get_info_from_the_web_page_original = get_get_info_from_the_web_page() +class WebPageInfo: + def get_info_from_the_web_page_f(self) -> Callable[[str], str]: + return get_get_info_from_the_web_page() DELEGATE_TASK_ERROR_MESSAGE = "An error occurred while trying to delegate the task to the selected team. Please try again." @@ -90,6 +92,8 @@ def create_brief_creation_team_toolbox( initial_brief=initial_brief, ) toolbox.set_context(context) + web_page_info = WebPageInfo() + web_page_info_f = web_page_info.get_info_from_the_web_page_f() @toolbox.add_function( "Get the TEMPLATE for the customer brief you will need to create" @@ -164,7 +168,7 @@ def get_info_from_the_web_page( url: Annotated[str, "The url of the web page which needs to be summarized"], context: Context, ) -> str: - result = _get_info_from_the_web_page_original(url) + result = web_page_info_f(url) if LAST_MESSAGE_BEGINNING in result: context.get_info_from_web_page_result += result + "\n\n" diff --git a/captn/captn_agents/backend/tools/_functions.py b/captn/captn_agents/backend/tools/_functions.py index d6aa41ca..2ca1ac8b 100644 --- a/captn/captn_agents/backend/tools/_functions.py +++ b/captn/captn_agents/backend/tools/_functions.py @@ -6,6 +6,7 @@ import time from collections import defaultdict from dataclasses import dataclass, field +from functools import lru_cache from typing import ( Annotated, Any, @@ -751,6 +752,7 @@ def get_get_info_from_the_web_page( But before giving up, please try to navigate to another page and continue with the task. Give up ONLY if you are sure that you can NOT retrieve any information!""" + @lru_cache(maxsize=20) def get_info_from_the_web_page( url: Annotated[str, "The url of the web page which needs to be summarized"], ) -> str: diff --git a/tests/ci/captn/captn_agents/backend/tools/test_functions.py b/tests/ci/captn/captn_agents/backend/tools/test_functions.py index 6a978f81..d14198d2 100644 --- a/tests/ci/captn/captn_agents/backend/tools/test_functions.py +++ b/tests/ci/captn/captn_agents/backend/tools/test_functions.py @@ -126,6 +126,32 @@ def test_get_webpage_status_code_returns_when_url_is_invalid(self): status_code = get_webpage_status_code(url=url) assert status_code == 404 + def test_get_info_from_the_web_page_cache(self): + url1 = "https://fakeurl1.com" + url2 = "https://fakeurl2.com" + + with unittest.mock.patch( + "captn.captn_agents.backend.tools._functions.get_webpage_status_code", + return_value=500, + ): + f = get_get_info_from_the_web_page() + f(url=url1) # miss + f(url=url1) # hit + f(url=url2) # miss + f(url=url2) # hit + f(url=url2) # hit + + cache_info = f.cache_info() + assert cache_info.hits == 3 + assert cache_info.misses == 2 + + f2 = get_get_info_from_the_web_page() + f2(url=url1) # miss + f2(url=url1) # hit + cache_info2 = f2.cache_info() + assert cache_info2.hits == 1 + assert cache_info2.misses == 1 + @pytest.mark.parametrize( "url", [