A scalable migration framework for migrating data from TestLink into BrowserStack Test Management.
Supports:
- MySQL / MariaDB
- Docker & On-Prem installations
- Native DB backups
- Attachment extraction
- Config extraction
- Canonical NDJSON exports
- BrowserStack API imports
- Resumable migrations
Organizations using TestLink often need to migrate:
- projects
- test suites
- test cases
- executions
- attachments
- plans
- custom fields
into BrowserStack Test Management.
However, TestLink data is distributed across:
- relational databases
- filesystem attachments
- config files
- execution history
This framework was designed to handle large-scale migrations safely and efficiently.
The system follows a two-phase hybrid migration architecture.
Extracts:
- native DB backup
- canonical NDJSON exports
- attachments
- config files
Outputs a reusable migration bundle.
Reads migration bundle and imports:
- projects
- folders
- testcases
- plans
- results
- attachments
using BrowserStack APIs.
The migration system combines:
- native DB backups
- NDJSON canonical exports
- zipped asset bundles
- decoupled API importer
This provides:
- resumability
- scalability
- portability
- low memory usage
- failure recovery
- large dataset support
.
├── browserstack/
├── extractor/
├── orchestrator/
├── utils/
├── mappings/
├── output/
├── requirements.txt
└── index.pyMain entrypoint.
Starts complete migration flow.
Master orchestration layer.
Handles:
- user prompts
- DB connection
- extraction
- migration flow
Canonical entity exporter.
Exports:
- projects
- suites
- testcases
- plans
- executions
- custom fields
into NDJSON format.
BrowserStack import coordinator.
Handles:
- project import
- folder import
- testcase import
- plan import
- results import
- attachment upload
- MySQL
- MariaDB
- PostgreSQL (planned)
- MSSQL (planned)
mysqldump \
-h localhost \
-P 3306 \
-u testlink \
-p testlink \
--single-transaction \
--quick \
--routines \
--triggers \
--events \
> backup.sqlCompressed:
mysqldump ... | gzip > backup.sql.gzpg_dump \
-h localhost \
-U postgres \
-d testlink \
-Fc \
-f backup.dumpsqlcmd -Q "
BACKUP DATABASE testlink
TO DISK='backup.bak'
"Extracts:
config_db.inc.phpcustom_config.inc.php
Docker example:
docker cp \
testlink:/var/www/html/testlink/config_db.inc.php .Compressed into:
configs.zip
Extracts assets from:
upload_area/
Supports:
- Docker
- on-prem filesystem
- future S3 support
Docker example:
docker cp \
testlink:/var/testlink/upload_area .Compressed into:
attachments.zip
The framework exports entities into:
NDJSON
Example:
{"id":1,"name":"Login Test"}
{"id":2,"name":"Checkout Test"}Benefits:
- streaming friendly
- low memory usage
- resumable imports
- chunk processing
- scalable for large datasets
Uses BrowserStack Test Management APIs for importing:
- projects
- folders
- testcases
- plans
- results
- attachments
Mappings are maintained for:
TestLink ID -> BrowserStack ID
Generated under:
mappings/
Examples:
projects.jsontestcases.jsonattachments.json
Used for:
- resumability
- attachment linking
- execution linking
Instead of recreating exact TestLink hierarchy, all suites are currently mapped into a single BrowserStack root folder:
TestLink Migrated
This improves:
- migration reliability
- API compatibility
- large dataset handling
while preserving original metadata.
Current limitations include:
- simplified suite hierarchy
- partial BrowserStack API restrictions
- PostgreSQL/MSSQL extractors still WIP
- attachment linking currently focused on testcase entities
Rejected because:
- tightly coupled
- difficult retries
- repeated DB access
Rejected because:
- weak hierarchy support
- attachment loss
- limited resumability
Rejected because:
- BrowserStack APIs still require transformed entities
Hybrid architecture combining:
- native backup
- canonical NDJSON
- zipped assets
- decoupled importer
provided the best balance.
- scalable
- resumable
- Docker compatible
- low memory usage
- attachment aware
- API-driven
- mapping based
- reusable migration bundles
- production-safe extraction flow
Planned enhancements:
- PostgreSQL extractor
- MSSQL extractor
- S3 attachment support
- rate limiting
- checkpoint recovery
- parallel imports
- exact suite hierarchy recreation
- incremental migrations
Create and activate a virtual environment:
python3 -m venv venv
source venv/bin/activateInstall Python dependencies:
pip3 install -r requirements.txtInstall the MySQL client:
brew install mysql-clientRun migration:
python3 index.pyoutput/
├── attachments/
├── configs/
├── db_backup/
├── entities/
└── logs/This project evolved from a simple DB backup script into a scalable migration framework by progressively solving:
- DB portability
- attachment handling
- hierarchy mapping
- resumability
- API integration
- large dataset processing
The final architecture separates:
- extraction
- transformation
- transport
- import
- mapping
into independent layers for better maintainability and operational safety.
