mirror of
https://github.com/apache/superset.git
synced 2026-04-07 18:35:15 +00:00
172 lines
5.4 KiB
Markdown
172 lines
5.4 KiB
Markdown
---
|
|
title: Backend Testing
|
|
sidebar_position: 3
|
|
---
|
|
|
|
<!--
|
|
Licensed to the Apache Software Foundation (ASF) under one
|
|
or more contributor license agreements. See the NOTICE file
|
|
distributed with this work for additional information
|
|
regarding copyright ownership. The ASF licenses this file
|
|
to you 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.
|
|
-->
|
|
|
|
# Backend Testing
|
|
|
|
🚧 **Coming Soon** 🚧
|
|
|
|
Complete guide for testing Superset's Python backend, APIs, and database interactions.
|
|
|
|
## Topics to be covered:
|
|
|
|
- Pytest configuration and fixtures
|
|
- Unit testing best practices
|
|
- Integration testing with databases
|
|
- API endpoint testing
|
|
- Mocking strategies and patterns
|
|
- Testing async operations with Celery
|
|
- Security testing guidelines
|
|
- Performance and load testing
|
|
- Test database setup and teardown
|
|
- Coverage requirements
|
|
|
|
## Quick Commands
|
|
|
|
```bash
|
|
# Run all backend tests
|
|
pytest
|
|
|
|
# Run specific test file
|
|
pytest tests/unit_tests/specific_test.py
|
|
|
|
# Run with coverage
|
|
pytest --cov=superset
|
|
|
|
# Run tests in parallel
|
|
pytest -n auto
|
|
|
|
# Run only unit tests
|
|
pytest tests/unit_tests/
|
|
|
|
# Run only integration tests
|
|
pytest tests/integration_tests/
|
|
```
|
|
|
|
## Testing Alerts & Reports with Celery and MailHog
|
|
|
|
The Alerts & Reports feature relies on Celery for task scheduling and execution. To test it locally, you need Redis (message broker), Celery Beat (scheduler), a Celery Worker (executor), and an SMTP server to receive email notifications.
|
|
|
|
### Prerequisites
|
|
|
|
- Redis running on `localhost:6379`
|
|
- [MailHog](https://github.com/mailhog/MailHog) installed (a local SMTP server with a web UI for viewing caught emails)
|
|
|
|
### superset_config.py
|
|
|
|
Your `CeleryConfig` **must** include `beat_schedule`. When you define a custom `CeleryConfig` class in `superset_config.py`, it replaces the default entirely. If you omit `beat_schedule`, Celery Beat will start but never schedule any report tasks.
|
|
|
|
```python
|
|
from celery.schedules import crontab
|
|
from superset.tasks.types import ExecutorType
|
|
|
|
REDIS_HOST = "localhost"
|
|
REDIS_PORT = "6379"
|
|
|
|
class CeleryConfig:
|
|
broker_url = f"redis://{REDIS_HOST}:{REDIS_PORT}/0"
|
|
result_backend = f"redis://{REDIS_HOST}:{REDIS_PORT}/0"
|
|
broker_connection_retry_on_startup = True
|
|
imports = (
|
|
"superset.sql_lab",
|
|
"superset.tasks.scheduler",
|
|
"superset.tasks.thumbnails",
|
|
"superset.tasks.cache",
|
|
)
|
|
worker_prefetch_multiplier = 10
|
|
task_acks_late = True
|
|
beat_schedule = {
|
|
"reports.scheduler": {
|
|
"task": "reports.scheduler",
|
|
"schedule": crontab(minute="*", hour="*"),
|
|
},
|
|
"reports.prune_log": {
|
|
"task": "reports.prune_log",
|
|
"schedule": crontab(minute=0, hour=0),
|
|
},
|
|
}
|
|
|
|
CELERY_CONFIG = CeleryConfig
|
|
|
|
# SMTP settings pointing to MailHog
|
|
SMTP_HOST = "localhost"
|
|
SMTP_PORT = 1025
|
|
SMTP_STARTTLS = False
|
|
SMTP_SSL = False
|
|
SMTP_USER = ""
|
|
SMTP_PASSWORD = ""
|
|
SMTP_MAIL_FROM = "superset@localhost"
|
|
|
|
# Must match where your frontend is running
|
|
WEBDRIVER_BASEURL = "http://localhost:9000/"
|
|
|
|
ALERT_REPORTS_EXECUTE_AS = [ExecutorType.OWNER]
|
|
|
|
FEATURE_FLAGS = {
|
|
"ALERT_REPORTS": True,
|
|
# Recommended for better screenshot support (WebGL/DeckGL charts)
|
|
"PLAYWRIGHT_REPORTS_AND_THUMBNAILS": True,
|
|
}
|
|
```
|
|
|
|
:::note
|
|
Do not include `"superset.tasks.async_queries"` in `CeleryConfig.imports` unless you need Global Async Queries. That module accesses `current_app.config` at import time and will crash the worker with a "Working outside of application context" error.
|
|
:::
|
|
|
|
### Starting the Services
|
|
|
|
Start MailHog, then Celery Beat and Worker in separate terminals:
|
|
|
|
```bash
|
|
# Terminal 1 - MailHog (SMTP on :1025, Web UI on :8025)
|
|
MailHog
|
|
|
|
# Terminal 2 - Celery Beat (scheduler)
|
|
celery --app=superset.tasks.celery_app:app beat --loglevel=info
|
|
|
|
# Terminal 3 - Celery Worker (executor)
|
|
celery --app=superset.tasks.celery_app:app worker --concurrency=1 --loglevel=info
|
|
```
|
|
|
|
Use `--concurrency=1` to limit resource usage on your dev machine.
|
|
|
|
### Verifying the Setup
|
|
|
|
1. **Beat** should log `Scheduler: Sending due task reports.scheduler (reports.scheduler)` once per minute
|
|
2. **Worker** should log `Scheduling alert <name> eta: <timestamp>` for each active report
|
|
3. Create a test report in **Settings > Alerts & Reports** with a `* * * * *` cron schedule
|
|
4. Check **http://localhost:8025** (MailHog web UI) for the email within 1-2 minutes
|
|
|
|
### Troubleshooting
|
|
|
|
| Problem | Solution |
|
|
|---|---|
|
|
| Beat shows no output | Ensure `beat_schedule` is defined in your `CeleryConfig` and `--loglevel=info` is set |
|
|
| "Report Schedule is still working, refusing to re-compute" | Previous executions are stuck. Reset with: `UPDATE report_schedule SET last_state = 'Not triggered' WHERE id = <id>;` |
|
|
| Task backlog overwhelming the worker | Flush Redis: `redis-cli FLUSHDB`, then restart Beat and Worker |
|
|
| Screenshot timeout | Ensure your frontend dev server is running and `WEBDRIVER_BASEURL` matches its URL |
|
|
|
|
---
|
|
|
|
*This documentation is under active development. Check back soon for updates!*
|