← Back to list

technical-debt-assessment
by aj-geddes
A curated collection of useful AI prompts for various tasks and use cases
⭐ 40🍴 4📅 Jan 23, 2026
SKILL.md
name: technical-debt-assessment description: Assess, quantify, and prioritize technical debt using code analysis, metrics, and impact analysis. Use when planning refactoring, evaluating codebases, or making architectural decisions.
Technical Debt Assessment
Overview
Systematically identify, measure, and manage technical debt to make informed decisions about code quality investments.
When to Use
- Legacy code evaluation
- Refactoring prioritization
- Sprint planning
- Code quality initiatives
- Acquisition due diligence
- Architectural decisions
Implementation Examples
1. Technical Debt Calculator
interface DebtItem {
id: string;
title: string;
description: string;
category: 'code' | 'architecture' | 'test' | 'documentation' | 'security';
severity: 'low' | 'medium' | 'high' | 'critical';
effort: number; // hours
impact: number; // 1-10 scale
interest: number; // cost per sprint if not fixed
}
class TechnicalDebtAssessment {
private items: DebtItem[] = [];
addDebtItem(item: DebtItem): void {
this.items.push(item);
}
calculatePriority(item: DebtItem): number {
const severityWeight = {
low: 1,
medium: 2,
high: 3,
critical: 4
};
const priority =
(item.impact * 10 + item.interest * 5 + severityWeight[item.severity] * 3) /
(item.effort + 1);
return priority;
}
getPrioritizedList(): Array<DebtItem & { priority: number }> {
return this.items
.map(item => ({
...item,
priority: this.calculatePriority(item)
}))
.sort((a, b) => b.priority - a.priority);
}
getDebtByCategory(): Record<string, DebtItem[]> {
return this.items.reduce((acc, item) => {
acc[item.category] = acc[item.category] || [];
acc[item.category].push(item);
return acc;
}, {} as Record<string, DebtItem[]>);
}
getTotalEffort(): number {
return this.items.reduce((sum, item) => sum + item.effort, 0);
}
getTotalInterest(): number {
return this.items.reduce((sum, item) => sum + item.interest, 0);
}
generateReport(): string {
const prioritized = this.getPrioritizedList();
const byCategory = this.getDebtByCategory();
let report = '# Technical Debt Assessment\n\n';
// Summary
report += '## Summary\n\n';
report += `- Total Items: ${this.items.length}\n`;
report += `- Total Effort: ${this.getTotalEffort()} hours\n`;
report += `- Monthly Interest: ${this.getTotalInterest()} hours\n\n`;
// By Category
report += '## By Category\n\n';
for (const [category, items] of Object.entries(byCategory)) {
const effort = items.reduce((sum, item) => sum + item.effort, 0);
report += `- ${category}: ${items.length} items (${effort} hours)\n`;
}
report += '\n';
// Top Priority Items
report += '## Top Priority Items\n\n';
for (const item of prioritized.slice(0, 10)) {
report += `### ${item.title} (Priority: ${item.priority.toFixed(2)})\n`;
report += `- Category: ${item.category}\n`;
report += `- Severity: ${item.severity}\n`;
report += `- Effort: ${item.effort} hours\n`;
report += `- Impact: ${item.impact}/10\n`;
report += `- Interest: ${item.interest} hours/sprint\n`;
report += `\n${item.description}\n\n`;
}
return report;
}
}
// Usage
const assessment = new TechnicalDebtAssessment();
assessment.addDebtItem({
id: 'debt-1',
title: 'Legacy API endpoints',
description: 'Old API v1 endpoints still in use, need migration',
category: 'architecture',
severity: 'high',
effort: 40,
impact: 8,
interest: 5
});
assessment.addDebtItem({
id: 'debt-2',
title: 'Missing unit tests',
description: '30% of codebase lacks test coverage',
category: 'test',
severity: 'medium',
effort: 80,
impact: 7,
interest: 3
});
console.log(assessment.generateReport());
2. Code Quality Scanner
import * as ts from 'typescript';
import * as fs from 'fs';
interface QualityIssue {
file: string;
line: number;
issue: string;
severity: 'info' | 'warning' | 'error';
debtHours: number;
}
class CodeQualityScanner {
private issues: QualityIssue[] = [];
scanProject(directory: string): QualityIssue[] {
this.issues = [];
const files = this.getTypeScriptFiles(directory);
for (const file of files) {
this.scanFile(file);
}
return this.issues;
}
private scanFile(filePath: string): void {
const sourceCode = fs.readFileSync(filePath, 'utf-8');
const sourceFile = ts.createSourceFile(
filePath,
sourceCode,
ts.ScriptTarget.Latest,
true
);
// Check for anti-patterns
this.checkForAnyTypes(sourceFile, filePath);
this.checkForLongFunctions(sourceFile, filePath);
this.checkForMagicNumbers(sourceFile, filePath);
this.checkForConsoleStatements(sourceFile, filePath);
this.checkForTodoComments(sourceFile, filePath);
}
private checkForAnyTypes(sourceFile: ts.SourceFile, filePath: string): void {
const visit = (node: ts.Node) => {
if (ts.isTypeReferenceNode(node) && node.typeName.getText() === 'any') {
const { line } = ts.getLineAndCharacterOfPosition(
sourceFile,
node.getStart()
);
this.issues.push({
file: filePath,
line: line + 1,
issue: 'Use of any type reduces type safety',
severity: 'warning',
debtHours: 0.5
});
}
ts.forEachChild(node, visit);
};
visit(sourceFile);
}
private checkForLongFunctions(sourceFile: ts.SourceFile, filePath: string): void {
const visit = (node: ts.Node) => {
if (ts.isFunctionDeclaration(node) || ts.isMethodDeclaration(node)) {
if (node.body) {
const lines = node.body.getFullText().split('\n').length;
if (lines > 50) {
const { line } = ts.getLineAndCharacterOfPosition(
sourceFile,
node.getStart()
);
this.issues.push({
file: filePath,
line: line + 1,
issue: `Function has ${lines} lines, should be refactored`,
severity: 'warning',
debtHours: Math.ceil(lines / 10)
});
}
}
}
ts.forEachChild(node, visit);
};
visit(sourceFile);
}
private checkForMagicNumbers(sourceFile: ts.SourceFile, filePath: string): void {
const visit = (node: ts.Node) => {
if (ts.isNumericLiteral(node)) {
const value = parseFloat(node.text);
// Ignore common constants
if (![0, 1, -1, 2].includes(value)) {
const { line } = ts.getLineAndCharacterOfPosition(
sourceFile,
node.getStart()
);
this.issues.push({
file: filePath,
line: line + 1,
issue: `Magic number ${value} should be a named constant`,
severity: 'info',
debtHours: 0.1
});
}
}
ts.forEachChild(node, visit);
};
visit(sourceFile);
}
private checkForConsoleStatements(sourceFile: ts.SourceFile, filePath: string): void {
const text = sourceFile.getFullText();
const lines = text.split('\n');
lines.forEach((line, index) => {
if (line.includes('console.log') || line.includes('console.error')) {
this.issues.push({
file: filePath,
line: index + 1,
issue: 'Console statement should use proper logger',
severity: 'info',
debtHours: 0.1
});
}
});
}
private checkForTodoComments(sourceFile: ts.SourceFile, filePath: string): void {
const text = sourceFile.getFullText();
const lines = text.split('\n');
lines.forEach((line, index) => {
if (/\/\/\s*TODO/.test(line)) {
this.issues.push({
file: filePath,
line: index + 1,
issue: 'TODO comment indicates incomplete work',
severity: 'warning',
debtHours: 2
});
}
});
}
private getTypeScriptFiles(dir: string): string[] {
// Implementation
return [];
}
getTotalDebt(): number {
return this.issues.reduce((sum, issue) => sum + issue.debtHours, 0);
}
generateReport(): string {
let report = '# Code Quality Report\n\n';
const bySeverity = this.issues.reduce((acc, issue) => {
acc[issue.severity] = acc[issue.severity] || [];
acc[issue.severity].push(issue);
return acc;
}, {} as Record<string, QualityIssue[]>);
report += `## Summary\n\n`;
report += `- Total Issues: ${this.issues.length}\n`;
report += `- Estimated Debt: ${this.getTotalDebt()} hours\n\n`;
for (const [severity, issues] of Object.entries(bySeverity)) {
report += `### ${severity.toUpperCase()} (${issues.length})\n\n`;
for (const issue of issues.slice(0, 10)) {
report += `- ${issue.file}:${issue.line} - ${issue.issue}\n`;
}
report += '\n';
}
return report;
}
}
Best Practices
✅ DO
- Quantify debt impact
- Prioritize by ROI
- Track debt over time
- Include debt in sprints
- Document debt decisions
- Set quality gates
❌ DON'T
- Ignore technical debt
- Fix everything at once
- Skip impact analysis
- Make emotional decisions
Debt Categories
- Code Quality: Complex code, duplicates
- Architecture: Poor design, tight coupling
- Testing: Missing tests, flaky tests
- Documentation: Missing docs, outdated
- Security: Vulnerabilities, outdated deps
- Performance: Inefficient code, N+1 queries
Resources
Score
Total Score
60/100
Based on repository quality metrics
✓SKILL.md
SKILL.mdファイルが含まれている
+20
✓LICENSE
ライセンスが設定されている
+10
○説明文
100文字以上の説明がある
0/10
○人気
GitHub Stars 100以上
0/15
○最近の活動
3ヶ月以内に更新がある
0/10
○フォーク
10回以上フォークされている
0/5
✓Issue管理
オープンIssueが50未満
+5
✓言語
プログラミング言語が設定されている
+5
○タグ
1つ以上のタグが設定されている
0/5
Reviews
💬
Reviews coming soon