Skip to content

Automated price monitoring for Fireaway Supply - Python/Playwright scraper, 284 products in 2min, CSV export, Slack alerts, Docker ready

Notifications You must be signed in to change notification settings

coder-r/fireaway-price-monitor

Folders and files

NameName
Last commit message
Last commit date

Latest commit

Β 

History

2 Commits
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 

Repository files navigation

πŸ”₯ Fireaway Supply Price Monitoring System

Automated web scraping system for monitoring product prices on fireawaysupply.co.uk with daily execution, change detection, and Slack notifications.

🎯 Features

  • βœ… Async Playwright browser automation
  • βœ… ~500 products across 9 categories
  • βœ… Price change detection with historical tracking
  • βœ… Stock availability monitoring
  • βœ… Slack Block Kit notifications
  • βœ… CSV exports (daily snapshots + changes)
  • βœ… AWS S3 backup (optional)
  • βœ… Docker support with multiple execution modes
  • βœ… Retry logic with exponential backoff
  • βœ… Error screenshots and alerts
  • βœ… Daily scheduling with APScheduler

πŸ“‹ Requirements

  • Python 3.11+
  • Docker (optional, recommended)
  • Slack webhook URL
  • AWS S3 credentials (optional)

πŸš€ Quick Start

Option 1: Docker (Recommended)

  1. Clone and configure:

    git clone <repo-url>
    cd price-updates
    cp .env.example .env
    # Edit .env with your credentials
  2. Build Docker image:

    chmod +x scripts/*.sh
    ./scripts/docker-build.sh
  3. Run in scheduled mode (daily at 2 AM):

    ./scripts/docker-run-scheduled.sh
  4. Or run once manually:

    ./scripts/docker-run-once.sh

Option 2: Local Python

  1. Setup virtual environment:

    python3.11 -m venv venv
    source venv/bin/activate  # or `venv\Scripts\activate` on Windows
  2. Install dependencies:

    pip install -r requirements.txt
    playwright install chromium
  3. Configure:

    cp .env.example .env
    # Edit .env with your Fireaway credentials and Slack webhook
  4. Run once:

    python src/main.py --mode once
  5. Run scheduled:

    python src/scheduler.py

βš™οΈ Configuration

All configuration via environment variables (.env file):

Required

  • FIREAWAY_USERNAME - Login username for Fireaway Supply portal
  • FIREAWAY_PASSWORD - Login password for Fireaway Supply portal

Optional

  • SLACK_WEBHOOK_URL - Slack webhook for notifications (highly recommended)
  • AWS_S3_ENABLED=false - Enable S3 backup for CSV files
  • AWS_S3_BUCKET - S3 bucket name
  • SCRAPE_SCHEDULE="0 2 * * *" - Cron schedule (default: 2 AM daily)
  • CONCURRENCY_LIMIT=3 - Number of parallel product scrapes
  • HEADLESS=true - Headless browser mode (false for debugging)
  • LOG_LEVEL=INFO - Logging level (DEBUG, INFO, WARNING, ERROR)

See .env.example for all available options.

πŸ“ Project Structure

price-updates/
β”œβ”€β”€ src/
β”‚   β”œβ”€β”€ scrapers/          # Web scraping modules
β”‚   β”‚   β”œβ”€β”€ browser.py     # Playwright browser setup
β”‚   β”‚   β”œβ”€β”€ auth.py        # Authentication logic
β”‚   β”‚   β”œβ”€β”€ category.py    # Category page scraper
β”‚   β”‚   └── product.py     # Product detail scraper
β”‚   β”œβ”€β”€ storage/           # Data persistence
β”‚   β”‚   β”œβ”€β”€ database.py    # SQLite operations
β”‚   β”‚   β”œβ”€β”€ csv_export.py  # CSV file generation
β”‚   β”‚   └── s3_uploader.py # AWS S3 backup
β”‚   β”œβ”€β”€ notifications/     # Alert systems
β”‚   β”‚   └── slack.py       # Slack Block Kit notifications
β”‚   β”œβ”€β”€ utils/             # Utilities
β”‚   β”‚   β”œβ”€β”€ logger.py      # Logging configuration
β”‚   β”‚   β”œβ”€β”€ retry.py       # Retry decorator
β”‚   β”‚   └── config.py      # Configuration loader
β”‚   β”œβ”€β”€ main.py            # Main entry point
β”‚   └── scheduler.py       # APScheduler setup
β”œβ”€β”€ data/
β”‚   β”œβ”€β”€ database.sqlite    # Historical product data
β”‚   β”œβ”€β”€ exports/           # CSV export files
β”‚   β”‚   β”œβ”€β”€ products_*.csv # Daily snapshots
β”‚   β”‚   └── changes_*.csv  # Price/stock changes
β”‚   └── screenshots/       # Error screenshots
β”œβ”€β”€ config/
β”‚   └── categories.json    # Category configuration
β”œβ”€β”€ docker/
β”‚   β”œβ”€β”€ Dockerfile
β”‚   └── docker-compose.yml
β”œβ”€β”€ scripts/               # Helper scripts
β”‚   β”œβ”€β”€ docker-build.sh
β”‚   β”œβ”€β”€ docker-run-once.sh
β”‚   └── docker-run-scheduled.sh
β”œβ”€β”€ tests/                 # Test suite
β”œβ”€β”€ requirements.txt       # Python dependencies
β”œβ”€β”€ .env.example           # Environment template
└── README.md              # This file

🐳 Docker Commands

Scheduled mode (runs continuously with daily execution):

docker-compose -f docker/docker-compose.yml up -d fireaway-scraper-scheduled
docker-compose -f docker/docker-compose.yml logs -f  # View logs
docker-compose -f docker/docker-compose.yml down     # Stop

One-shot mode (manual execution):

docker-compose -f docker/docker-compose.yml --profile manual run --rm fireaway-scraper-once

Test mode (dry run):

docker-compose -f docker/docker-compose.yml --profile test run --rm fireaway-scraper-test

πŸ“Š CSV Output

Full Snapshot (products_YYYY-MM-DD_HH-MM-SS.csv):

sku,name,category,price_current,price_original,stock_status,url,image_url,last_checked
FA-001,Product Name,Food,15.99,19.99,in-stock,https://...,https://...,2025-11-06 02:00:00

Changes Report (changes_YYYY-MM-DD_HH-MM-SS.csv):

timestamp,sku,name,change_type,old_value,new_value,price_diff,price_diff_percent
2025-11-06 02:00:00,FA-001,Product Name,price_decrease,19.99,15.99,-4.00,-20.01%

πŸ”” Slack Notifications

Rich formatted messages with:

  • πŸ“‰ Price decreases (with % and absolute difference)
  • πŸ“ˆ Price increases (with alert emoji)
  • βœ… Stock now available (out-of-stock β†’ in-stock)
  • ❌ Out of stock (in-stock β†’ out-of-stock)
  • πŸ†• New products (first-time detection)

Example notification:

πŸ”₯ Fireaway Supply - Price Update Alert

πŸ“‰ Price Decreased
Product Name
Β£19.99 β†’ Β£15.99 (-Β£4.00, -20.01%)
Category: Food | SKU: FA-001

πŸ§ͺ Testing

Test authentication:

python src/main.py --test-auth

Test Slack notifications:

python src/main.py --test-slack

Run full test suite:

pytest tests/ -v

Test with visible browser (debugging):

HEADLESS=false python src/main.py --mode once

πŸ“ˆ Performance

  • Execution time: ~15-20 minutes (for ~500 products)
  • Products monitored: ~500 across 9 categories
  • Concurrency: 3 parallel product scrapes (configurable)
  • Memory usage: ~500MB (Playwright browser + data)
  • Storage growth: ~5-10MB per daily run (SQLite + CSVs)
  • Network: ~100-200 HTTP requests per run

πŸ› οΈ Development

Install dev dependencies:

pip install -r requirements-dev.txt

Code formatting:

black src/ tests/

Linting:

pylint src/

Type checking:

mypy src/

Run tests with coverage:

pytest tests/ --cov=src --cov-report=html

πŸ” Security

  • ⚠️ Never commit .env file (added to .gitignore)
  • πŸ”’ Use Docker secrets in production
  • πŸ”‘ Rotate credentials regularly
  • πŸ›‘οΈ Limit S3 bucket access with IAM policies
  • πŸ“Έ Screenshots may contain sensitive data - secure storage location
  • πŸ” Use environment-specific .env files (.env.prod, .env.dev)

πŸ› Troubleshooting

Authentication fails

  • βœ… Check username/password in .env
  • βœ… Try with HEADLESS=false to see browser behavior
  • βœ… Check error screenshots in data/screenshots/
  • βœ… Verify website is accessible and login page hasn't changed

Slack notifications not working

  • βœ… Verify webhook URL format is correct
  • βœ… Test with python src/main.py --test-slack
  • βœ… Check webhook permissions in Slack workspace
  • βœ… Review logs for notification errors

S3 upload fails

  • βœ… Check AWS credentials are valid
  • βœ… Verify bucket exists and region is correct
  • βœ… Ensure IAM user has s3:PutObject permission
  • βœ… Test AWS CLI: aws s3 ls s3://your-bucket-name/

Performance issues

  • ⬇️ Reduce CONCURRENCY_LIMIT (try 1 or 2)
  • ⏱️ Increase REQUEST_DELAY_MS (try 3000-5000)
  • 🧹 Clean up old screenshots and CSV exports
  • πŸ’Ύ Check disk space for database growth

Products not being scraped

  • βœ… Check config/categories.json - all categories enabled?
  • βœ… Verify website structure hasn't changed (selectors)
  • βœ… Check logs for scraping errors
  • βœ… Try scraping single category first

Docker container exits immediately

  • βœ… Check logs: docker-compose logs fireaway-scraper-scheduled
  • βœ… Verify .env file is mounted correctly
  • βœ… Ensure all required env variables are set
  • βœ… Check for Python syntax errors in logs

πŸ“‹ Maintenance

Regular tasks

  • πŸ“… Weekly: Review logs for errors
  • πŸ“… Monthly: Backup database file
  • πŸ“… Monthly: Clean up old CSV exports
  • πŸ“… Quarterly: Update dependencies (pip install -U -r requirements.txt)
  • πŸ“… Quarterly: Review and optimize database (SQLite VACUUM)

Database maintenance

# Backup database
cp data/database.sqlite data/database_backup_$(date +%Y%m%d).sqlite

# Optimize database
sqlite3 data/database.sqlite "VACUUM;"

# Check database size
du -h data/database.sqlite

Log rotation

# Archive old logs
gzip data/scraper.log
mv data/scraper.log.gz data/logs/scraper_$(date +%Y%m%d).log.gz

πŸ”„ Scaling

For more products

  • Increase CONCURRENCY_LIMIT (4-6 with good connection)
  • Adjust REQUEST_DELAY_MS to balance speed vs. politeness
  • Consider running multiple scrapers for different category groups

For production deployment

  • Use managed scheduling (AWS EventBridge, Google Cloud Scheduler)
  • Store database in persistent volume or managed database
  • Use managed Slack app instead of webhooks
  • Implement monitoring (Datadog, New Relic)
  • Add alerting for scraper failures

πŸ“Š Monitoring

Key metrics to track

  • βœ… Scrape execution time
  • βœ… Number of products scraped
  • βœ… Number of price changes detected
  • βœ… Error rate
  • βœ… Database size growth
  • βœ… Memory usage

Health checks

# Check last successful run
sqlite3 data/database.sqlite "SELECT MAX(last_checked) FROM products;"

# Count products in database
sqlite3 data/database.sqlite "SELECT COUNT(*) FROM products;"

# Check for recent errors
tail -n 100 data/scraper.log | grep ERROR

🎯 Roadmap

  • Web dashboard for viewing price history
  • Email notifications (alternative to Slack)
  • Price alerts with custom thresholds
  • Product filtering by category/price range
  • Historical price charts
  • API endpoint for querying data
  • Multi-site support (expand beyond Fireaway)
  • Machine learning for price prediction

πŸ“ License

MIT License

Copyright (c) 2025

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

🀝 Contributing

Contributions are welcome! Please follow these guidelines:

  1. Fork the repository
  2. Create a feature branch (git checkout -b feature/amazing-feature)
  3. Commit your changes (git commit -m 'Add amazing feature')
  4. Push to the branch (git push origin feature/amazing-feature)
  5. Open a Pull Request

Code style

  • Follow PEP 8
  • Use type hints
  • Add docstrings to functions
  • Write tests for new features

Commit messages

feat: Add price prediction model
fix: Handle missing product images
docs: Update installation instructions
test: Add integration tests for S3 upload

πŸ“§ Support

πŸ™ Acknowledgments


Made with ❀️ for efficient price monitoring

About

Automated price monitoring for Fireaway Supply - Python/Playwright scraper, 284 products in 2min, CSV export, Slack alerts, Docker ready

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published