diff --git a/nova-act/README.md b/nova-act/README.md index 55d90f60..8f67afc8 100644 --- a/nova-act/README.md +++ b/nova-act/README.md @@ -12,6 +12,7 @@ Nova Act enables developers to build intelligent agents that can interact with w - **Integrate seamlessly** with Python code for testing, assertions, and debugging The SDK works in conjunction with **Amazon Bedrock AgentCore Browser**, a secure, cloud-based browser environment that provides: + - Session isolation and security - Built-in observability (live viewing, CloudTrail logging, session replay) - Containerized ephemeral environments @@ -38,12 +39,14 @@ Automate quality assurance testing for web applications using Nova Act and Agent - **Integration with pytest** for comprehensive test reporting and CI/CD pipelines **Key Benefits:** + - Reduce test maintenance overhead by 40-60% - Execute comprehensive test suites in minutes instead of hours - Eliminate false negatives from UI changes - Scale testing across browsers, devices, and environments effortlessly **What's Included:** + - Sample retail web application for testing - 15 ready-to-use JSON test cases - Pytest framework with parallel execution support @@ -52,15 +55,44 @@ Automate quality assurance testing for web applications using Nova Act and Agent [→ Explore the QA Testing Use Case](./usecases/qa-testing/) +### 💰 [Price Comparison](./usecases/price_comparison/) + +Automate product price comparison across multiple retailers using Nova Act. This use case showcases: + +- **Intelligent product search** that navigates retail websites and finds matching products +- **Concurrent execution** across multiple retailers for faster price discovery +- **Structured data extraction** using Pydantic schemas for reliable pricing information +- **Captcha handling** with user prompts for manual intervention when needed +- **CSV export** for easy analysis and comparison of results + +**Key Benefits:** + +- Compare prices across Amazon, Best Buy, Costco, Target, and more in minutes +- Reduce manual price checking effort by automating browser navigation +- Get structured output with product names, prices, and promotion details +- Easily customize product searches and retailer sources via CLI arguments + +**What's Included:** + +- Ready-to-run price comparison script +- Support for custom product SKUs and retailer sources +- Pydantic-based data validation for extracted pricing +- ThreadPoolExecutor for parallel retailer searches +- Complete setup and usage instructions + +[→ Explore the Price Comparison Use Case](./usecases/price_comparison/) + ## Why Agentic Workflows? Traditional automation approaches face significant challenges: + - **High maintenance overhead**: Scripts break with UI changes, requiring constant updates - **Limited scalability**: Manual testing is time-intensive and incomplete - **Technical barriers**: Creating automation requires specialized programming knowledge - **Brittleness**: Automation relies on specific selectors that fail when components change Agentic AI with Nova Act addresses these challenges by: + - **Adapting dynamically** to interface changes without manual updates - **Mimicking human interaction** patterns for realistic testing - **Enabling non-technical users** to create tests through simple JSON definitions @@ -81,6 +113,7 @@ This project is licensed under the MIT-0 License. See the [LICENSE](../LICENSE) ## Support For questions, issues, or feature requests: + - Open an issue in this repository - Refer to the [official Nova Act documentation](https://github.com/aws/nova-act) - Contact AWS Support for enterprise assistance diff --git a/nova-act/usecases/price_comparison/README.md b/nova-act/usecases/price_comparison/README.md new file mode 100644 index 00000000..0b8261e2 --- /dev/null +++ b/nova-act/usecases/price_comparison/README.md @@ -0,0 +1,162 @@ +# Price Comparison using Amazon Nova Act + +This project demonstrates automated price comparison across multiple retailers using Amazon Nova Act. It showcases how AI-powered browser agents can intelligently search for products, navigate retail websites, and extract pricing information to help consumers find the best deals. + +## Overview + +This demonstration implements a concurrent price comparison workflow that searches for products across major retailers (e.g. Amazon, Best Buy, Costco, Target) and compiles results into a sortable comparison table. + +### Key Benefits + +- **Automated Price Discovery**: AI agents navigate retail sites and extract current pricing +- **Concurrent Execution**: Parallel searches across multiple retailers reduce total execution time +- **Structured Output**: Results exported to CSV for easy analysis and comparison +- **Flexible Configuration**: Customize product searches and retailer sources + +## Architecture + +The demo consists of two main components: + +1. **Nova Act Browser Agents**: Automated browser sessions that navigate retail websites, handle captchas, and extract product information +2. **Concurrent Execution Engine**: ThreadPoolExecutor manages parallel searches across multiple retailers + +## Prerequisites + +Before running this demo, ensure you have: + +### Development Environment + +- **Python 3.11 or higher** +- **pip** (Python package manager) + +### API Access + +- **Amazon Nova Act API Key** - Visit [Nova Act home page](https://nova.amazon.com/act) to generate your API key + +## Getting Started + +Follow these steps to set up and run the price comparison tool: + +### Step 1: Install Dependencies + +```bash +# Navigate to the project directory +cd nova-act/usecases/price_comparison + +# Create and activate virtual environment +python -m venv venv +source venv/bin/activate # On Windows: venv\Scripts\activate + +# Install dependencies +pip install -r requirements.txt +``` + +### Step 2: Configure API Key + +Set your Nova Act API key as an environment variable: + +```bash +export NOVA_ACT_API_KEY="your-api-key-here" +``` + +### Step 3: Run Price Comparison + +```bash +# Run with default product (iPad Pro 13-inch M4, 256GB Wi-Fi) +python main.py + +# Run with custom product +python main.py --product_name "iPhone 15 Pro Max 256GB" --product_sku "MU793LL/A" + +# Run with custom sources +python main.py --sources '[("Walmart", "https://www.walmart.com"), ("Amazon", "https://www.amazon.com")]' + +# Run in non-headless mode (visible browser) +python main.py --headless=False +``` + +## Usage Examples + +### Default Search + +```bash +python main.py +``` + +Searches for "iPad Pro 13-inch (M4 chip), 256GB Wi-Fi" (SKU: MVX23LL/A) across Amazon, Best Buy, Costco, and Target. + +### Custom Product Search + +```bash +python main.py --product_name "MacBook Air 13-inch M3" --product_sku "MRXN3LL/A" +``` + +### Custom Retailer Sources + +```bash +python main.py --sources '[("Walmart", "https://www.walmart.com"), ("Newegg", "https://www.newegg.com")]' +``` + +### Debug Mode (Visible Browser) + +```bash +python main.py --headless=False +``` + +## Output + +Results are saved to `price_comparison_results.csv` with the following columns: + +| Column | Description | +| ----------------- | ---------------------------------------- | +| Source | Retailer name (Amazon, Best Buy, etc.) | +| Product Name | Matched product name from retailer | +| Product SKU | Search SKU used | +| Price | Current price (sorted lowest to highest) | +| Promotion Details | Any active promotions or discounts | + +## Project Structure + +``` +price_comparison/ +├── README.md # This file +├── main.py # Main application script +└── requirements.txt # Python dependencies +``` + +## How It Works + +1. **Initialization**: Creates Nova Act browser sessions for each retailer +2. **Captcha Handling**: Detects captchas and prompts user to solve if needed +3. **Product Search**: Searches using the product SKU on each retailer site +4. **Result Extraction**: AI agent identifies the most relevant product and extracts pricing +5. **Data Compilation**: Results are aggregated, sorted by price, and exported to CSV + +## Troubleshooting + +### Common Issues + +1. **Captcha Detected** + + - The tool will pause and prompt you to solve the captcha manually + - Press Enter after solving to continue + +2. **Product Not Found** + + - Verify the SKU is valid for the target retailers + - Some products may not be available at all retailers + +3. **Browser Session Errors** + + - Ensure you have a stable internet connection + - Try running in non-headless mode to debug: `--headless=False` + +4. **API Key Issues** + ```bash + export NOVA_ACT_API_KEY="your-api-key-here" + ``` + +## Additional Resources + +- [Amazon Nova Act](https://nova.amazon.com/act) +- [Nova Act Documentation](https://docs.aws.amazon.com/nova/latest/userguide/what-is-nova.html) diff --git a/nova-act/usecases/price_comparison/main.py b/nova-act/usecases/price_comparison/main.py new file mode 100644 index 00000000..08f4747b --- /dev/null +++ b/nova-act/usecases/price_comparison/main.py @@ -0,0 +1,172 @@ +# Copyright 2025 Amazon Inc + +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +"""Compare product prices across multiple retailers. + +Searches for a product across Amazon, Best Buy, Costco, and Target concurrently +and displays pricing and promotion details in a comparison table. + +Usage: + python main.py [--product_name ] [--product_sku ] [--sources ] [--headless] + python main.py --product_name "iPad Pro 13-inch, 256GB Wi-Fi" --product_sku "MVX23LL/A" + python main.py --sources '[("Walmart", "https://www.walmart.com"), ("Amazon", "https://www.amazon.com")]' + python main.py --headless=False +""" + +from concurrent.futures import ThreadPoolExecutor, as_completed + +import fire +import pandas as pd +from nova_act import BOOL_SCHEMA, ActAgentError, NovaAct +from pydantic import BaseModel + +# Global defaults +DEFAULT_PRODUCT_NAME = "iPad Pro 13-inch (M4 chip), 256GB Wi-Fi" +DEFAULT_PRODUCT_SKU = "MVX23LL/A" +DEFAULT_PRODUCT_SOURCES = [ + # ("Amazon", "https://www.amazon.com"), + ("Best Buy", "https://www.bestbuy.com"), + ("Costco", "https://www.costco.com"), + ("Target", "https://www.target.com"), +] + + +class ProductPricing(BaseModel): + product_name: str | None + price: float | None + promotion_details: str | None + source: str # Target, Best Buy, or Costco + + +def check_source_price( + product_name: str, + product_sku: str, + source: str, + starting_url: str, + headless: bool = True, +) -> ProductPricing | None: + """Check price for a product at a specific source.""" + + try: + with NovaAct(starting_page=starting_url, headless=headless) as nova: + # Check for captcha + captcha_check = nova.act_get( + "Is there a captcha on the screen?", schema=BOOL_SCHEMA + ) + if captcha_check.matches_schema and captcha_check.parsed_response: + input(f"Please solve the captcha for {source} and hit return when done") + + # Search using product SKU + nova.act_get(f"Search for '{product_sku}'.") + + # Extract pricing and details from the most relevant result based on product name + result = nova.act_get( + f""" + Close any popups if they appear. + Review all search results and determine which one is the most relevant to the product name '{product_name}'. + Select this item to navigate to the product page. + Then, extract the price and any promotion details from the most relevant result that matches the product name '{product_name}'. + If no matching product exists, return None for all fields except source. Do not attempt to re-search using a different keyword combination. + """, + schema=ProductPricing.model_json_schema(), + ) + + if not result.matches_schema: + print(f"Invalid JSON from {source}: {result}") + return None + + pricing = ProductPricing.model_validate(result.parsed_response) + return pricing + + except ActAgentError as exc: + print(f"Could not retrieve pricing from {source}: {exc}") + return None + + +def main( + product_name: str | None = None, + product_sku: str | None = None, + sources: list[tuple[str, str]] = DEFAULT_PRODUCT_SOURCES, + headless: bool = True, +) -> None: + """Search for product prices across multiple sources concurrently.""" + # Validate that both product_name and product_sku are provided together + if (product_name is None) != (product_sku is None): + raise ValueError( + "Both product_name and product_sku must be provided together. " + "You cannot specify only one without the other." + ) + + # Use defaults if neither was provided + if product_name is None: + product_name = DEFAULT_PRODUCT_NAME + product_sku = DEFAULT_PRODUCT_SKU + + all_prices = [] + + print( + f"Searching for '{product_name}' (SKU: {product_sku}) across {len(sources)} sources...\n" + ) + + with ThreadPoolExecutor() as executor: + future_to_source = { + executor.submit( + check_source_price, + product_name, + product_sku, + source_name, + source_url, + headless, + ): source_name + for source_name, source_url in sources + } + + for future in as_completed(future_to_source.keys()): + source = future_to_source[future] + pricing = future.result() + + if pricing is not None: + result_dict = pricing.model_dump() + result_dict["sku"] = product_sku + all_prices.append(result_dict) + else: + all_prices.append( + { + "source": source, + "product_name": None, + "sku": product_sku, + "price": None, + "promotion_details": None, + } + ) + + # Create DataFrame and sort by price + df = pd.DataFrame(all_prices) + df = df.sort_values(by="price", na_position="last") + + # Reorder columns + df = df[["source", "product_name", "sku", "price", "promotion_details"]] + + # Rename columns for better readability in output + df.columns = ["Source", "Product Name", "Product SKU", "Price", "Promotion Details"] + + # Write results to CSV + output_file = "price_comparison_results.csv" + df.to_csv(output_file, index=False) + + print(f"\nResults written to {output_file}") + + +if __name__ == "__main__": + fire.Fire(main) diff --git a/nova-act/usecases/price_comparison/requirements.txt b/nova-act/usecases/price_comparison/requirements.txt new file mode 100644 index 00000000..cfb05637 --- /dev/null +++ b/nova-act/usecases/price_comparison/requirements.txt @@ -0,0 +1,19 @@ +cryptography +fire +install_playwright +jsonschema +numpy<=2.2.6 +pandas +pillow +playwright>=1.54.0 +pydantic>=2.10.6 +requests +retry +pytz +strands-agents>=0.1.9 +strands-agents-tools +Deprecated +boto3 +boto3-stubs +mypy-boto3-s3 +nova-act==3.0.67.0