# GitLab MCP Integration Testing Architecture
## Overview
The GitLab MCP integration tests follow a **dependency chain pattern** to ensure efficient testing with real GitLab data while minimizing API spam and resource usage.
## π Test Dependency Chain
```
π data-lifecycle.test.ts
β Creates complete test infrastructure
β
βββ π schemas-dependent/merge-requests.test.ts
βββ π schemas-dependent/repository.test.ts
βββ π workitems.test.ts
βββ ... (other schema tests)
β All use the shared infrastructure
β
π§Ή Cleanup (only at the very end)
```
## π¨ Critical Rules
1. **Tests CANNOT run standalone** - They depend on lifecycle data
2. **Must use `--runInBand`** - Tests must run serially to maintain dependencies
3. **Single infrastructure creation** - Only data-lifecycle.test.ts creates data
4. **No individual cleanup** - Only final cleanup in data-lifecycle.test.ts
5. **Real data only** - No mocks, all tests use actual GitLab entities
## π File Structure
```
tests/
βββ integration/
β βββ data-lifecycle.test.ts # π Creates ALL test infrastructure
β βββ schemas-dependent/ # π Tests using lifecycle data
β β βββ merge-requests.test.ts # π MR schema tests with real MRs
β β βββ repository.test.ts # π³ Repo schema tests with real files
β β βββ ... # π Other schema tests
β βββ schemas/workitems.test.ts # π GraphQL tests with real work items
βββ setup/
β βββ testConfig.ts # π§ Shared configuration
β βββ sequencer.js # π Test execution order
β βββ globalSetup.js # π Pre-test validation
β βββ globalTeardown.js # π§Ή Post-test summary
βββ jest.config.js # βοΈ Jest configuration for all tests
```
## π How to Run Tests
### Complete Integration Test Suite (Recommended)
```bash
yarn test
```
This command:
- β
Uses all feature flags (WORKITEMS, MILESTONE, PIPELINE, GITLAB_WIKI)
- β
Runs tests in dependency order with `--runInBand`
- β
Creates complete infrastructure once
- β
Tests all schemas with real data
- β
Cleans up everything at the end
### Individual Test Files (NOT RECOMMENDED)
```bash
# β DON'T DO THIS - Will fail due to missing dependencies
yarn test tests/integration/schemas-dependent/merge-requests.test.ts
# β
If you must, run the full chain:
yarn test
```
## π Data Lifecycle Stages
### Stage 1: Foundation (data-lifecycle.test.ts)
```typescript
// Creates in dependency order:
1. Test Group (contains everything)
2. Test Project (in the group)
3. Repository Files (README, src/, docs/, .gitignore)
4. Feature Branches (feature/*, hotfix/*)
5. Repository Tags (v1.0.0, v1.1.0)
6. Labels (bug, feature, enhancement)
7. Milestones (Sprint 1, Release 1.0)
8. Work Items (Issue, Epic, Task)
9. Merge Requests (from feature branches)
```
### Stage 2: Schema Validation (schemas-dependent/*.test.ts)
```typescript
// Uses the created infrastructure to test:
- π ListMergeRequestsSchema with real MRs
- π³ GetRepositoryTreeSchema with real files
- π All other schemas with their respective real data
- π Real data validation without soft-fail patterns
```
### Stage 3: GraphQL Testing (schemas/workitems.test.ts)
```typescript
// Tests GraphQL operations with:
- π Real work items from lifecycle
- π Schema introspection
- π§© Dynamic query building with real widgets
```
### Stage 4: Cleanup (data-lifecycle.test.ts afterAll)
```typescript
// Single cleanup operation:
- ποΈ Delete test group (cascades to all projects, MRs, work items)
- β
Complete infrastructure removal
```
## π§ Configuration
### Environment Variables
```bash
# Required for all tests
GITLAB_TOKEN=glpat-xxx...
GITLAB_API_URL=https://gitlab.com
# Optional for specific project testing (can be blank)
GITLAB_PROJECT_ID=
# Feature flags (automatically set by test:integration:lifecycle)
USE_WORKITEMS=true
USE_MILESTONE=true
USE_PIPELINE=true
USE_GITLAB_WIKI=true
```
### Test Data Access
```typescript
// In any dependent test file:
import { requireTestData, getTestProject } from '../../setup/testConfig';
describe('My Schema Tests', () => {
let testData: any;
let testProject: any;
beforeAll(async () => {
// This will throw if lifecycle tests haven't run
testData = requireTestData();
testProject = getTestProject();
});
it('should test with real data', async () => {
// Use testProject.id, testData.mergeRequests, etc.
const response = await fetch(`${GITLAB_API_URL}/api/v4/projects/${testProject.id}/...`);
// Test with real GitLab data
});
});
```
## β οΈ Common Issues
### "Test data not available"
```
Error: Test data not available. Make sure to run data-lifecycle.test.ts first with --runInBand
```
**Solution:** Use `yarn test` instead of individual test files.
### Tests running in parallel
```
Tests create multiple conflicting infrastructures
```
**Solution:** Always use `--runInBand` flag for integration tests.
### Missing dependencies
```
Test expects MRs but none found
```
**Solution:** Ensure data-lifecycle.test.ts completed successfully and shared the data.
## π Benefits
1. **Efficient**: Single infrastructure creation vs. per-test creation
2. **Fast**: No repeated setup/teardown cycles
3. **Realistic**: Tests use actual GitLab entities with real relationships
4. **Reliable**: Dependency chain ensures data consistency
5. **Clean**: Single cleanup operation at the end
6. **Maintainable**: Clear separation between data creation and testing
## β
Current Status (2025-01-15)
**π ALL CRITICAL ISSUES RESOLVED**:
- β
**Complete test suite passing** - 27/27 test suites, 369/372 tests passing (99.2%)
- β
**Unit tests completely rewritten** - Proper mock infrastructure using enhancedFetch
- β
**Integration tests fully working** - Real GitLab API testing with data lifecycle
- β
**Node-fetch migration complete** - All tests now use native fetch API
- β
**Test dependency chain FIXED** - Persistent file storage enables data sharing between test files
- β
**Soft-fail patterns eliminated** - All tests use real data or fail properly
- β
**Jest configuration enhanced** - Proper serial execution with `--runInBand`
**Test Results Summary**:
- **Total Test Suites**: 27 passed, 0 failed
- **Total Tests**: 369 passed, 3 skipped, 0 failed (372 total)
- **Integration Tests**: 16 suites passing (200+ tests)
- **Unit Tests**: 11 suites passing (169+ tests)
- **Coverage**: 54.92% statements, 37.39% branches, 53.28% functions
**Key Test Categories**:
- β
**Data Lifecycle**: 12/12 tests passing - Complete infrastructure setup/teardown
- β
**Schema Validation**: 150+ tests passing - All GitLab API schemas validated
- β
**Unit Tests**: 169+ tests passing - Full mock-based handler testing
- β
**Work Items GraphQL**: 20+ tests passing - Full CRUD with real GitLab instance
- β
**Integration API**: 30+ tests passing - Real GitLab API validation
## π― Adding New Tests
To add a new schema test:
1. Create file in `schemas-dependent/your-schema.test.ts`
2. Import shared config: `import { requireTestData } from '../../setup/testConfig'`
3. Use lifecycle data: `const testData = requireTestData()`
4. Test with real entities from lifecycle
5. Add to sequencer.js if order matters
6. No individual cleanup needed
The dependency chain pattern ensures your test will have real data to work with while maintaining efficiency and preventing API spam.