Awesome-claude-code estimate-pipeline-time
Estimates and optimizes CI/CD pipeline execution time. Analyzes job dependencies, identifies bottlenecks, and suggests parallelization strategies.
git clone https://github.com/dykyi-roman/awesome-claude-code
T=$(mktemp -d) && git clone --depth=1 https://github.com/dykyi-roman/awesome-claude-code "$T" && mkdir -p ~/.claude/skills && cp -r "$T/skills/estimate-pipeline-time" ~/.claude/skills/dykyi-roman-awesome-claude-code-estimate-pipeline-time && rm -rf "$T"
skills/estimate-pipeline-time/SKILL.mdPipeline Time Estimator
Estimates pipeline execution time and identifies optimization opportunities.
Pipeline Analysis
Execution Flow Visualization
┌─────────────────────────────────────────────────────────────────┐ │ PIPELINE EXECUTION FLOW │ ├─────────────────────────────────────────────────────────────────┤ │ │ │ Time 0 2 4 6 8 10 12 14 16 18 20 │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ ▼ ▼ ▼ ▼ ▼ ▼ ▼ ▼ ▼ ▼ ▼ │ │ │ │ install ████████ │ │ │ │ │ ├──▶ phpstan ████████ │ │ │ │ │ ├──▶ psalm ██████████ │ │ │ │ │ ├──▶ cs-fixer ██████ │ │ │ │ │ └──▶ deptrac ████ │ │ │ │ │ └──▶ test-unit ████████████████ │ │ │ │ │ └──▶ build ████│ │ │ │ Critical Path: install → psalm → test-unit → build = 20 min │ │ │ └─────────────────────────────────────────────────────────────────┘
Time Estimation Model
Job Time Components
Job Time = Setup Time + Execution Time + Teardown Time Where: - Setup Time = Runner startup + Checkout + Cache restore - Execution Time = Actual command execution - Teardown Time = Artifact upload + Cache save + Cleanup
Typical Job Times (PHP Project)
| Job | Cold (no cache) | Warm (cached) | Components |
|---|---|---|---|
| checkout | 10s | 10s | git clone |
| composer install | 180s | 30s | Download + autoload |
| phpstan | 120s | 120s | Analysis |
| psalm | 180s | 180s | Analysis + taint |
| cs-fixer | 60s | 60s | Style check |
| deptrac | 30s | 30s | Architecture |
| phpunit (unit) | 120s | 120s | Tests |
| phpunit (integration) | 300s | 300s | Tests + DB |
| docker build | 600s | 120s | Build + push |
Critical Path Analysis
# Pseudo-algorithm for critical path def find_critical_path(jobs): # Build dependency graph graph = build_dependency_graph(jobs) # Calculate earliest start time for each job for job in topological_sort(graph): job.earliest_start = max( dep.earliest_finish for dep in job.dependencies ) if job.dependencies else 0 job.earliest_finish = job.earliest_start + job.duration # Total pipeline time = max(earliest_finish) total_time = max(job.earliest_finish for job in jobs) # Critical path = jobs where slack = 0 critical_path = [job for job in jobs if job.slack == 0] return critical_path, total_time
Optimization Strategies
1. Parallelize Independent Jobs
# BEFORE: Sequential (20 min) # install → phpstan → psalm → cs-fixer → deptrac → test → build # AFTER: Parallel lint (12 min) # install ─┬─► phpstan ─────┐ # ├─► psalm ───────┼─► test → build # ├─► cs-fixer ────┤ # └─► deptrac ─────┘ # Savings: 8 minutes (40%)
2. Split Long Jobs
# BEFORE: Single test job (10 min) test: script: vendor/bin/phpunit # AFTER: Parallel test suites (4 min) test-unit: script: vendor/bin/phpunit --testsuite=unit test-integration: script: vendor/bin/phpunit --testsuite=integration test-e2e: script: vendor/bin/phpunit --testsuite=e2e # Savings: 6 minutes (60%)
3. Optimize Cache Usage
# BEFORE: No caching (composer install: 3 min) - run: composer install # AFTER: With caching (composer install: 30 sec) - uses: actions/cache@v4 with: path: | ~/.composer/cache vendor key: composer-${{ hashFiles('composer.lock') }} - run: composer install # Savings: 2.5 minutes per job
4. Use Smaller Images
# BEFORE: Full PHP image (pull: 45 sec) image: php:8.4-cli # AFTER: Alpine image (pull: 15 sec) image: php:8.4-cli-alpine # Savings: 30 seconds per job
5. Matrix Optimization
# BEFORE: Matrix of 9 combinations, all run strategy: matrix: php: ['8.2', '8.3', '8.4'] deps: ['lowest', 'locked', 'highest'] # AFTER: Strategic subset (3 combinations) strategy: matrix: include: - php: '8.2' deps: 'lowest' # Min requirements - php: '8.4' deps: 'locked' # Primary target - php: '8.4' deps: 'highest' # Future compat # Savings: 66% reduction in matrix jobs
Analysis Output Format
# Pipeline Time Analysis **Pipeline:** CI **Current Duration:** 25 min 30 sec **Optimized Estimate:** 10 min 15 sec **Potential Savings:** 15 min 15 sec (60%) ## Current Execution Timeline
Job Start Duration End Status ────────────────────────────────────────────────────────── install 0:00 3:00 3:00 ✓ phpstan 3:00 2:00 5:00 ✓ (waits 3:00) psalm 5:00 3:00 8:00 ✓ (waits 5:00) cs-fixer 8:00 1:00 9:00 ✓ (waits 8:00) deptrac 9:00 0:30 9:30 ✓ (waits 9:00) test-unit 9:30 6:00 15:30 ✓ (waits 9:30) test-integration 15:30 8:00 23:30 ✓ (waits 15:30) build 23:30 2:00 25:30 ✓ (waits 23:30)
## Critical Path
install (3:00) → psalm (3:00) → test-unit (6:00) → test-integration (8:00) → build (2:00) Total: 22:00 (critical path determines minimum possible time)
## Bottleneck Analysis | Job | Duration | Wait Time | Utilization | Bottleneck? | |-----|----------|-----------|-------------|-------------| | install | 3:00 | 0:00 | 100% | No | | phpstan | 2:00 | 3:00 | 40% | **Wait** | | psalm | 3:00 | 5:00 | 37% | **Wait** | | cs-fixer | 1:00 | 8:00 | 11% | **Wait** | | test-integration | 8:00 | 15:30 | 34% | **Duration** | ## Optimization Recommendations ### 1. Parallelize Lint Jobs **Impact:** -6:30 (25%) ```yaml # Current: Sequential # Proposed: All lint jobs run in parallel after install
2. Split Integration Tests
Impact: -4:00 (16%)
# Current: Single 8-minute job # Proposed: Split into 3 parallel jobs of ~3 min each
3. Add Caching
Impact: -2:30 (10%)
# Current: Cold composer install (3:00) # Proposed: Cached install (0:30)
4. Move Build Earlier
Impact: -0:30 (2%)
# Build can start after unit tests, doesn't need integration
Optimized Pipeline
Time 0 2 4 6 8 10 │ │ │ │ │ │ ▼ ▼ ▼ ▼ ▼ ▼ install (0:30) ─┬─► phpstan (2:00) ──────────┐ ├─► psalm (3:00) ────────────┼─► test-unit (4:00) ─┬─► build (2:00) ├─► cs-fixer (1:00) ─────────┤ │ └─► deptrac (0:30) ──────────┘ │ │ test-int-1 (3:00) ───────────────────┤ test-int-2 (3:00) ───────────────────┤ test-int-3 (3:00) ───────────────────┘ Total: 10:15 (was 25:30)
Summary
| Metric | Before | After | Change |
|---|---|---|---|
| Total Duration | 25:30 | 10:15 | -60% |
| Critical Path | 22:00 | 10:15 | -53% |
| Parallelism | 12% | 68% | +56% |
| Wait Time | 41:30 | 8:00 | -81% |
## Estimation Formulas ### Total Pipeline Time
T_total = max(T_critical_path, T_resource_constrained)
Where: T_critical_path = sum of job times on longest dependency chain T_resource_constrained = total_job_time / max_parallel_runners
### Cache Benefit
T_cached = T_uncached * cache_hit_rate * cache_speedup + T_uncached * (1 - cache_hit_rate)
Example:
- Uncached composer: 180s
- Cache hit rate: 90%
- Cache speedup: 85% T_cached = 180 * 0.90 * 0.15 + 180 * 0.10 = 24.3 + 18 = 42s
## Usage Provide: - CI configuration file - Historical run data (optional) - Runner constraints (optional) The estimator will: 1. Parse job dependencies 2. Estimate job durations 3. Calculate critical path 4. Identify bottlenecks 5. Suggest optimizations 6. Estimate savings