The Tusk Drift Node SDK is a Node.js library that enables recording and replaying of both outbound and inbound network calls. This allows you to capture real API interactions during development and replay them during testing, ensuring consistent and reliable test execution without external dependencies.
The SDK instruments various Node.js libraries (http, https, fetch, pg, postgres, etc.) to intercept and record network traffic. During replay mode, the SDK matches incoming requests against recorded traces and returns the previously captured responses.
This guide provides step-by-step instructions for iterating on SDK instrumentations when debugging E2E tests. Use this when:
- An E2E test endpoint is failing
- You need to debug or fix instrumentation code
- You want to verify that SDK changes work correctly
E2E tests are located in src/instrumentation/libraries/{library}/e2e-tests/{module-type}-{library}/:
Each test directory contains:
src/- Test application source codeDockerfile- Container configurationdocker-compose.yml- Container orchestration.tusk/- Traces and logs directoryrun.sh- Automated test runner
cd src/instrumentation/libraries/{library}/e2e-tests/{test-name}Example:
cd src/instrumentation/libraries/http/e2e-tests/cjs-httpBefore running a new test iteration, delete existing traces and logs to ensure only current test data is present:
rm -rf .tusk/traces/*
rm -rf .tusk/logs/*This prevents confusion from old test runs and makes it easier to identify current issues.
Build and start the Docker container in detached mode:
docker compose up -d --build --waitInstall dependencies (now that /sdk volume is mounted):
docker compose exec -T app npm installStart the application server in RECORD mode to capture network traffic:
docker compose exec -d -e TUSK_DRIFT_MODE=RECORD app sh -c "npm run build && npm run dev"Wait a few seconds for the server to fully start (5-10 seconds recommended):
sleep 5Use curl to make requests to the endpoints you want to test. You can hit one or multiple endpoints:
# Example: GET request
docker compose exec app curl -s http://localhost:3000/test/fetch-get
# Example: POST request with JSON body
docker compose exec app curl -s -X POST -H "Content-Type: application/json" \
-d '{"title":"test","body":"test body"}' \
http://localhost:3000/test/fetch-postTip: Check the test's src/index.ts file to see all available endpoints.
Wait a few seconds to ensure all traces are written to local storage:
sleep 3Stop the Node.js server process:
docker compose exec app pkill -f "node" || true
sleep 2Run the Tusk CLI to replay the recorded traces:
docker compose exec -T -e TUSK_ANALYTICS_DISABLED=1 app tusk drift run --print --output-format "json" --enable-service-logsFlags explained:
--print- Print test results to stdout--output-format "json"- Output results in JSON format--enable-service-logs- Write detailed service logs to.tusk/logs/for debugging
To see all available flags, run:
tusk drift run --helpInterpreting Results:
The output will be JSON with test results:
[
{
"test_id": "test-1",
"passed": true,
"duration": 150
},
{
"test_id": "test-2",
"passed": false,
"duration": 200
}
]"passed": true- Test passed successfully"passed": false- Test failed (mismatch between recording and replay)- Check
.tusk/logs/for detailed error messages and debugging information
If tests fail, check the service logs for detailed error information:
If you deleted the logs before running the test, there should be only 1 log file in the .tusk/logs/ directory.
You can also view the traces recorded in the .tusk/traces/ directory.
When you need to fix instrumentation code:
-
Make changes to the SDK source code
-
Rebuild the SDK from the repository root:
npm run build
-
NO need to rebuild Docker containers - the SDK is mounted as a volume, so changes propagate automatically
-
Clean up traces and logs (Step 2)
-
Restart the server in RECORD mode (Step 4)
-
Hit the endpoints again (Step 5)
-
Run the CLI tests (Step 8)
-
Repeat until tests pass
When you're done testing, clean up the Docker containers:
docker compose downThe Docker Compose configuration mounts the SDK source code as a read-only volume:
volumes:
- ../../../../../..:/sdk:ro # SDK source mounted at /sdkThis means:
- ✅ SDK changes propagate automatically - no need to rebuild containers
- ✅ Fast iteration - just run
npm run buildin the SDK root - ❌ Must rebuild SDK - changes won't take effect until you run
npm run build
- Traces (
.tusk/traces/) - Recorded network interactions - Logs (
.tusk/logs/) - Detailed service logs when--enable-service-logsis used - Always clean these before re-running tests to avoid confusion
- Check service logs first - Most issues are explained in
.tusk/logs/ - Verify traces were created - Check
.tusk/traces/has files after recording - Test one endpoint at a time - Easier to isolate issues
- Check for TCP warnings - Indicates missing instrumentation
Each E2E test directory has a run.sh script that automates the entire workflow:
./run.shThis script:
- Cleans traces and logs
- Starts containers
- Starts server in RECORD mode
- Hits all endpoints
- Runs CLI tests
- Displays results with colored output
- Checks for TCP instrumentation warnings
- Cleans up containers, traces, and logs
- Exits with code 0 (success) or 1 (failure)
Use run.sh for full test runs, and use the manual steps above for iterative debugging.
# Clean traces and logs
rm -rf .tusk/traces/* .tusk/logs/*
# Start containers
docker compose up -d --build
# Install dependencies
docker compose exec -T app npm install
# Start server in RECORD mode
docker compose exec -d -e TUSK_DRIFT_MODE=RECORD app sh -c "npm run build && npm run dev"
# Stop server
docker compose exec app pkill -f "node" || true
# Run tests
docker compose exec -T -e TUSK_ANALYTICS_DISABLED=1 app tusk drift run --print --output-format "json" --enable-service-logs
# View logs
docker compose exec app ls .tusk/logs
docker compose exec app cat .tusk/logs/<log-file>
# Rebuild SDK (from repo root)
npm run build
# Clean up containers
docker compose down
# Run full automated test
./run.sh