@democratize-quality/qualitylens-core 0.2.6 → 0.2.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/core/config.d.mts +3 -2
- package/dist/core/config.d.ts +3 -2
- package/dist/core/config.js +10 -7
- package/dist/core/config.js.map +1 -1
- package/dist/core/config.mjs +10 -7
- package/dist/core/config.mjs.map +1 -1
- package/dist/core/types.d.mts +63 -3
- package/dist/core/types.d.ts +63 -3
- package/dist/core/types.js.map +1 -1
- package/package.json +1 -1
package/dist/core/types.d.mts
CHANGED
|
@@ -9,6 +9,7 @@ type CoverageStatus = 'automated' | 'manual' | 'both' | 'none';
|
|
|
9
9
|
type TestSource = 'playwright' | 'ado' | 'yaml' | 'csv';
|
|
10
10
|
type Staleness = 'fresh' | 'stale' | 'unknown';
|
|
11
11
|
type TestHintStatus = 'resolved' | 'gap' | 'acknowledged' | 'ignore';
|
|
12
|
+
type ActionHintStatus = 'covered' | 'gap' | 'acknowledged';
|
|
12
13
|
interface TestHint {
|
|
13
14
|
test: string;
|
|
14
15
|
status: TestHintStatus;
|
|
@@ -18,6 +19,16 @@ interface TestHint {
|
|
|
18
19
|
confidence?: 'high' | 'medium' | 'low';
|
|
19
20
|
resolvedBy?: string;
|
|
20
21
|
}
|
|
22
|
+
/** An AI or human resolution for an action coverage gap (Pro) */
|
|
23
|
+
interface ActionHint {
|
|
24
|
+
route: string;
|
|
25
|
+
action: string;
|
|
26
|
+
status: ActionHintStatus;
|
|
27
|
+
coveredByTest?: string;
|
|
28
|
+
priority?: 'p1' | 'p2' | 'p3';
|
|
29
|
+
reason?: string;
|
|
30
|
+
resolvedBy?: string;
|
|
31
|
+
}
|
|
21
32
|
interface AppRoute {
|
|
22
33
|
path: string;
|
|
23
34
|
method?: string;
|
|
@@ -29,6 +40,7 @@ interface TestEntry {
|
|
|
29
40
|
filePath?: string;
|
|
30
41
|
lastRun?: Date;
|
|
31
42
|
tags?: string[];
|
|
43
|
+
steps?: string;
|
|
32
44
|
}
|
|
33
45
|
interface RouteGap {
|
|
34
46
|
route: string;
|
|
@@ -70,6 +82,52 @@ interface CoverageReport {
|
|
|
70
82
|
unmatchedTests: TestEntry[];
|
|
71
83
|
routeGaps: RouteGap[];
|
|
72
84
|
acknowledgedTests: TestHint[];
|
|
85
|
+
actionCoverage?: RouteActionCoverage[];
|
|
86
|
+
actionSummary?: {
|
|
87
|
+
totalActions: number;
|
|
88
|
+
coveredActions: number;
|
|
89
|
+
coveragePercent: number;
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
/** A user-facing action discovered in the application component tree (Pro) */
|
|
93
|
+
interface AppAction {
|
|
94
|
+
label: string;
|
|
95
|
+
type: 'handler' | 'button' | 'form' | 'link';
|
|
96
|
+
sourceFile: string;
|
|
97
|
+
handlerName?: string;
|
|
98
|
+
category?: 'primary' | 'error-recovery';
|
|
99
|
+
}
|
|
100
|
+
/** An action extracted from a test — Playwright body or CSV step text (Pro) */
|
|
101
|
+
interface TestAction {
|
|
102
|
+
label: string;
|
|
103
|
+
routePath: string;
|
|
104
|
+
type: 'goto' | 'click' | 'fill' | 'submit';
|
|
105
|
+
testTitle?: string;
|
|
106
|
+
filePath?: string;
|
|
107
|
+
}
|
|
108
|
+
/** Per-route action coverage — app actions vs what tests exercise (Pro) */
|
|
109
|
+
interface RouteActionCoverage {
|
|
110
|
+
routePath: string;
|
|
111
|
+
discoveredActions: AppAction[];
|
|
112
|
+
coveredActions: string[];
|
|
113
|
+
uncoveredActions: AppAction[];
|
|
114
|
+
errorScenarioActions?: AppAction[];
|
|
115
|
+
note?: string;
|
|
116
|
+
aiResolvedActions?: Array<{
|
|
117
|
+
label: string;
|
|
118
|
+
reason?: string;
|
|
119
|
+
coveredByTest?: string;
|
|
120
|
+
}>;
|
|
121
|
+
prioritisedGaps?: {
|
|
122
|
+
p1: AppAction[];
|
|
123
|
+
p2: AppAction[];
|
|
124
|
+
p3: AppAction[];
|
|
125
|
+
unclassified: AppAction[];
|
|
126
|
+
};
|
|
127
|
+
gapHints?: Record<string, {
|
|
128
|
+
reason?: string;
|
|
129
|
+
resolvedBy?: string;
|
|
130
|
+
}>;
|
|
73
131
|
}
|
|
74
132
|
interface TestGapConfig {
|
|
75
133
|
projectName: string;
|
|
@@ -93,11 +151,12 @@ interface TestGapConfig {
|
|
|
93
151
|
planId: number;
|
|
94
152
|
patEnvVar: string;
|
|
95
153
|
};
|
|
96
|
-
csv?: {
|
|
154
|
+
csv?: Array<{
|
|
97
155
|
path: string;
|
|
98
156
|
titleField: string;
|
|
99
157
|
dateField?: string;
|
|
100
|
-
|
|
158
|
+
stepsField?: string;
|
|
159
|
+
}>;
|
|
101
160
|
manualCoverage?: {
|
|
102
161
|
route: string;
|
|
103
162
|
lastTested: string;
|
|
@@ -109,6 +168,7 @@ interface TestGapConfig {
|
|
|
109
168
|
minCoverage: number;
|
|
110
169
|
}[];
|
|
111
170
|
testHints?: TestHint[];
|
|
171
|
+
actionHints?: ActionHint[];
|
|
112
172
|
}
|
|
113
173
|
|
|
114
|
-
export type { AppRoute, AreaCoverage, CoverageReport, CoverageStatus, RouteCoverage, RouteGap, Staleness, TestEntry, TestGapConfig, TestHint, TestHintStatus, TestSource };
|
|
174
|
+
export type { ActionHint, ActionHintStatus, AppAction, AppRoute, AreaCoverage, CoverageReport, CoverageStatus, RouteActionCoverage, RouteCoverage, RouteGap, Staleness, TestAction, TestEntry, TestGapConfig, TestHint, TestHintStatus, TestSource };
|
package/dist/core/types.d.ts
CHANGED
|
@@ -9,6 +9,7 @@ type CoverageStatus = 'automated' | 'manual' | 'both' | 'none';
|
|
|
9
9
|
type TestSource = 'playwright' | 'ado' | 'yaml' | 'csv';
|
|
10
10
|
type Staleness = 'fresh' | 'stale' | 'unknown';
|
|
11
11
|
type TestHintStatus = 'resolved' | 'gap' | 'acknowledged' | 'ignore';
|
|
12
|
+
type ActionHintStatus = 'covered' | 'gap' | 'acknowledged';
|
|
12
13
|
interface TestHint {
|
|
13
14
|
test: string;
|
|
14
15
|
status: TestHintStatus;
|
|
@@ -18,6 +19,16 @@ interface TestHint {
|
|
|
18
19
|
confidence?: 'high' | 'medium' | 'low';
|
|
19
20
|
resolvedBy?: string;
|
|
20
21
|
}
|
|
22
|
+
/** An AI or human resolution for an action coverage gap (Pro) */
|
|
23
|
+
interface ActionHint {
|
|
24
|
+
route: string;
|
|
25
|
+
action: string;
|
|
26
|
+
status: ActionHintStatus;
|
|
27
|
+
coveredByTest?: string;
|
|
28
|
+
priority?: 'p1' | 'p2' | 'p3';
|
|
29
|
+
reason?: string;
|
|
30
|
+
resolvedBy?: string;
|
|
31
|
+
}
|
|
21
32
|
interface AppRoute {
|
|
22
33
|
path: string;
|
|
23
34
|
method?: string;
|
|
@@ -29,6 +40,7 @@ interface TestEntry {
|
|
|
29
40
|
filePath?: string;
|
|
30
41
|
lastRun?: Date;
|
|
31
42
|
tags?: string[];
|
|
43
|
+
steps?: string;
|
|
32
44
|
}
|
|
33
45
|
interface RouteGap {
|
|
34
46
|
route: string;
|
|
@@ -70,6 +82,52 @@ interface CoverageReport {
|
|
|
70
82
|
unmatchedTests: TestEntry[];
|
|
71
83
|
routeGaps: RouteGap[];
|
|
72
84
|
acknowledgedTests: TestHint[];
|
|
85
|
+
actionCoverage?: RouteActionCoverage[];
|
|
86
|
+
actionSummary?: {
|
|
87
|
+
totalActions: number;
|
|
88
|
+
coveredActions: number;
|
|
89
|
+
coveragePercent: number;
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
/** A user-facing action discovered in the application component tree (Pro) */
|
|
93
|
+
interface AppAction {
|
|
94
|
+
label: string;
|
|
95
|
+
type: 'handler' | 'button' | 'form' | 'link';
|
|
96
|
+
sourceFile: string;
|
|
97
|
+
handlerName?: string;
|
|
98
|
+
category?: 'primary' | 'error-recovery';
|
|
99
|
+
}
|
|
100
|
+
/** An action extracted from a test — Playwright body or CSV step text (Pro) */
|
|
101
|
+
interface TestAction {
|
|
102
|
+
label: string;
|
|
103
|
+
routePath: string;
|
|
104
|
+
type: 'goto' | 'click' | 'fill' | 'submit';
|
|
105
|
+
testTitle?: string;
|
|
106
|
+
filePath?: string;
|
|
107
|
+
}
|
|
108
|
+
/** Per-route action coverage — app actions vs what tests exercise (Pro) */
|
|
109
|
+
interface RouteActionCoverage {
|
|
110
|
+
routePath: string;
|
|
111
|
+
discoveredActions: AppAction[];
|
|
112
|
+
coveredActions: string[];
|
|
113
|
+
uncoveredActions: AppAction[];
|
|
114
|
+
errorScenarioActions?: AppAction[];
|
|
115
|
+
note?: string;
|
|
116
|
+
aiResolvedActions?: Array<{
|
|
117
|
+
label: string;
|
|
118
|
+
reason?: string;
|
|
119
|
+
coveredByTest?: string;
|
|
120
|
+
}>;
|
|
121
|
+
prioritisedGaps?: {
|
|
122
|
+
p1: AppAction[];
|
|
123
|
+
p2: AppAction[];
|
|
124
|
+
p3: AppAction[];
|
|
125
|
+
unclassified: AppAction[];
|
|
126
|
+
};
|
|
127
|
+
gapHints?: Record<string, {
|
|
128
|
+
reason?: string;
|
|
129
|
+
resolvedBy?: string;
|
|
130
|
+
}>;
|
|
73
131
|
}
|
|
74
132
|
interface TestGapConfig {
|
|
75
133
|
projectName: string;
|
|
@@ -93,11 +151,12 @@ interface TestGapConfig {
|
|
|
93
151
|
planId: number;
|
|
94
152
|
patEnvVar: string;
|
|
95
153
|
};
|
|
96
|
-
csv?: {
|
|
154
|
+
csv?: Array<{
|
|
97
155
|
path: string;
|
|
98
156
|
titleField: string;
|
|
99
157
|
dateField?: string;
|
|
100
|
-
|
|
158
|
+
stepsField?: string;
|
|
159
|
+
}>;
|
|
101
160
|
manualCoverage?: {
|
|
102
161
|
route: string;
|
|
103
162
|
lastTested: string;
|
|
@@ -109,6 +168,7 @@ interface TestGapConfig {
|
|
|
109
168
|
minCoverage: number;
|
|
110
169
|
}[];
|
|
111
170
|
testHints?: TestHint[];
|
|
171
|
+
actionHints?: ActionHint[];
|
|
112
172
|
}
|
|
113
173
|
|
|
114
|
-
export type { AppRoute, AreaCoverage, CoverageReport, CoverageStatus, RouteCoverage, RouteGap, Staleness, TestEntry, TestGapConfig, TestHint, TestHintStatus, TestSource };
|
|
174
|
+
export type { ActionHint, ActionHintStatus, AppAction, AppRoute, AreaCoverage, CoverageReport, CoverageStatus, RouteActionCoverage, RouteCoverage, RouteGap, Staleness, TestAction, TestEntry, TestGapConfig, TestHint, TestHintStatus, TestSource };
|
package/dist/core/types.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/core/types.ts"],"sourcesContent":["/**\n * src/core/types.ts\n * \n * ALL shared interfaces live here.\n * Every other file in this project imports types from this file.\n * Do not scatter interface definitions — keep this as the single source of truth.\n */\n\nexport type CoverageStatus = 'automated' | 'manual' | 'both' | 'none'\nexport type TestSource = 'playwright' | 'ado' | 'yaml' | 'csv'\nexport type Staleness = 'fresh' | 'stale' | 'unknown'\nexport type TestHintStatus = 'resolved' | 'gap' | 'acknowledged' | 'ignore'\n\nexport interface TestHint {\n test: string // exact test title to match\n status: TestHintStatus // resolved | gap | acknowledged | ignore\n route?: string // route path — for resolved + gap\n method?: string // HTTP method — for gap (e.g. DELETE, PATCH)\n reason?: string\n confidence?: 'high' | 'medium' | 'low'\n resolvedBy?: string // 'agent' | 'human' | 'ai'\n}\n\nexport interface AppRoute {\n path: string // e.g. /checkout/payment\n method?: string // GET | POST | etc — from OpenAPI\n area?: string // populated by AreaMatcher\n}\n\nexport interface TestEntry {\n title: string\n source: TestSource\n filePath?: string // playwright: which spec file\n lastRun?: Date // manual: from yaml or ADO\n tags?: string[]\n}\n\nexport interface RouteGap {\n route: string\n method?: string\n reason?: string\n coveredByTests: TestEntry[]\n}\n\nexport interface RouteCoverage {\n route: AppRoute\n status: CoverageStatus\n automatedTests: TestEntry[]\n manualTests: TestEntry[]\n staleness: Staleness\n lastTestedAt?: Date\n notes?: string\n}\n\nexport interface AreaCoverage {\n name: string\n routes: RouteCoverage[]\n totalRoutes: number\n coveredRoutes: number\n automatedCount: number\n manualOnlyCount: number\n noCoverageCount: number\n coveragePercent: number // 0-100, rounded integer\n}\n\nexport interface CoverageReport {\n generatedAt: Date\n projectName: string\n summary: {\n totalRoutes: number\n totalCoverage: number\n automatedCoverage: number\n manualOnlyCoverage: number\n noCoverage: number\n }\n areas: AreaCoverage[]\n uncategorised: RouteCoverage[]\n unmatchedTests: TestEntry[] // still unresolved — no hint applied\n routeGaps: RouteGap[] // tests targeting routes not in schema (gap hints)\n acknowledgedTests: TestHint[] // acknowledged or ignored hints\n}\n\nexport interface TestGapConfig {\n projectName: string\n staleThresholdDays: number\n routes: {\n type: 'nextjs' | 'express' | 'openapi' | 'manual'\n path: string\n generate?: string // shell command to run before route discovery (e.g. to produce openapi.json)\n basePath?: string // prefix stripped when grouping routes into areas (e.g. /api, /api/v1)\n }\n tests?: {\n path: string // directory to scan for *.spec.ts / *.test.ts files\n // relative to qualitylens.yaml location\n // default: same directory as qualitylens.yaml\n }\n areas: {\n name: string\n patterns: string[]\n }[]\n ado?: {\n orgUrl: string\n project: string\n planId: number\n patEnvVar: string // env var name — never hardcode the PAT value\n }\n csv?: {\n path: string //
|
|
1
|
+
{"version":3,"sources":["../../src/core/types.ts"],"sourcesContent":["/**\n * src/core/types.ts\n * \n * ALL shared interfaces live here.\n * Every other file in this project imports types from this file.\n * Do not scatter interface definitions — keep this as the single source of truth.\n */\n\nexport type CoverageStatus = 'automated' | 'manual' | 'both' | 'none'\nexport type TestSource = 'playwright' | 'ado' | 'yaml' | 'csv'\nexport type Staleness = 'fresh' | 'stale' | 'unknown'\nexport type TestHintStatus = 'resolved' | 'gap' | 'acknowledged' | 'ignore'\nexport type ActionHintStatus = 'covered' | 'gap' | 'acknowledged'\n\nexport interface TestHint {\n test: string // exact test title to match\n status: TestHintStatus // resolved | gap | acknowledged | ignore\n route?: string // route path — for resolved + gap\n method?: string // HTTP method — for gap (e.g. DELETE, PATCH)\n reason?: string\n confidence?: 'high' | 'medium' | 'low'\n resolvedBy?: string // 'agent' | 'human' | 'ai'\n}\n\n/** An AI or human resolution for an action coverage gap (Pro) */\nexport interface ActionHint {\n route: string // route path e.g. /account\n action: string // action label e.g. \"Delete Account\"\n status: ActionHintStatus // covered | gap | acknowledged\n coveredByTest?: string // which test covers it (for status: covered)\n priority?: 'p1' | 'p2' | 'p3' // gap priority — p1 = must fix, p3 = nice to have\n reason?: string // explanation\n resolvedBy?: string // 'ai' | 'human'\n}\n\nexport interface AppRoute {\n path: string // e.g. /checkout/payment\n method?: string // GET | POST | etc — from OpenAPI\n area?: string // populated by AreaMatcher\n}\n\nexport interface TestEntry {\n title: string\n source: TestSource\n filePath?: string // playwright: which spec file\n lastRun?: Date // manual: from yaml or ADO\n tags?: string[]\n steps?: string // raw step text from CSV stepsField — used by Pro action extractor\n}\n\nexport interface RouteGap {\n route: string\n method?: string\n reason?: string\n coveredByTests: TestEntry[]\n}\n\nexport interface RouteCoverage {\n route: AppRoute\n status: CoverageStatus\n automatedTests: TestEntry[]\n manualTests: TestEntry[]\n staleness: Staleness\n lastTestedAt?: Date\n notes?: string\n}\n\nexport interface AreaCoverage {\n name: string\n routes: RouteCoverage[]\n totalRoutes: number\n coveredRoutes: number\n automatedCount: number\n manualOnlyCount: number\n noCoverageCount: number\n coveragePercent: number // 0-100, rounded integer\n}\n\nexport interface CoverageReport {\n generatedAt: Date\n projectName: string\n summary: {\n totalRoutes: number\n totalCoverage: number\n automatedCoverage: number\n manualOnlyCoverage: number\n noCoverage: number\n }\n areas: AreaCoverage[]\n uncategorised: RouteCoverage[]\n unmatchedTests: TestEntry[] // still unresolved — no hint applied\n routeGaps: RouteGap[] // tests targeting routes not in schema (gap hints)\n acknowledgedTests: TestHint[] // acknowledged or ignored hints\n actionCoverage?: RouteActionCoverage[] // Pro: per-route action gap analysis\n actionSummary?: { // Pro: aggregate action coverage metric\n totalActions: number\n coveredActions: number\n coveragePercent: number\n }\n}\n\n/** A user-facing action discovered in the application component tree (Pro) */\nexport interface AppAction {\n label: string // \"Delete Account\", \"Place Order\", \"Apply Promo Code\"\n type: 'handler' | 'button' | 'form' | 'link'\n sourceFile: string // component file where it was found\n handlerName?: string // e.g. handleDeleteAccount (if type === 'handler')\n category?: 'primary' | 'error-recovery' // error-recovery = only shown in error state (Retry, Try again, etc.)\n}\n\n/** An action extracted from a test — Playwright body or CSV step text (Pro) */\nexport interface TestAction {\n label: string // extracted text: \"Delete Account\", \"Place Order\"\n routePath: string // route this action targets (from page.goto context or step URL)\n type: 'goto' | 'click' | 'fill' | 'submit'\n testTitle?: string // which test this came from\n filePath?: string // source file\n}\n\n/** Per-route action coverage — app actions vs what tests exercise (Pro) */\nexport interface RouteActionCoverage {\n routePath: string\n discoveredActions: AppAction[] // primary actions found in component tree\n coveredActions: string[] // labels matched by at least one test action\n uncoveredActions: AppAction[] // gap — exists in app, no test exercises it\n errorScenarioActions?: AppAction[] // error-recovery actions (Retry, Try again, etc.) — separate consideration\n note?: string // e.g. \"delegates to <CartView /> — partial scan\"\n // AI-enhanced fields — populated when actionHints are present\n aiResolvedActions?: Array<{ // actions confirmed covered by AI after reviewing test code\n label: string\n reason?: string\n coveredByTest?: string\n }>\n prioritisedGaps?: { // remaining gaps grouped by priority from actionHints\n p1: AppAction[]\n p2: AppAction[]\n p3: AppAction[]\n unclassified: AppAction[]\n }\n gapHints?: Record<string, { reason?: string; resolvedBy?: string }> // keyed by action label — AI-generated context for each gap\n}\n\nexport interface TestGapConfig {\n projectName: string\n staleThresholdDays: number\n routes: {\n type: 'nextjs' | 'express' | 'openapi' | 'manual'\n path: string\n generate?: string // shell command to run before route discovery (e.g. to produce openapi.json)\n basePath?: string // prefix stripped when grouping routes into areas (e.g. /api, /api/v1)\n }\n tests?: {\n path: string // directory to scan for *.spec.ts / *.test.ts files\n // relative to qualitylens.yaml location\n // default: same directory as qualitylens.yaml\n }\n areas: {\n name: string\n patterns: string[]\n }[]\n ado?: {\n orgUrl: string\n project: string\n planId: number\n patEnvVar: string // env var name — never hardcode the PAT value\n }\n csv?: Array<{\n path: string // path to a specific CSV file (relative to qualitylens.yaml)\n titleField: string // column name that holds the test title\n dateField?: string // optional: column with last-run date (ISO 8601)\n stepsField?: string // optional: column with free-form test step text (Pro action extraction)\n }>\n manualCoverage?: {\n route: string\n lastTested: string // ISO date string\n tester?: string\n notes?: string\n }[]\n thresholds?: {\n area?: string // area name or '*' for global\n minCoverage: number // 0-100\n }[]\n testHints?: TestHint[]\n actionHints?: ActionHint[]\n}\n"],"mappings":";;;;;;;;;;;;;;;;AAAA;AAAA;","names":[]}
|
package/package.json
CHANGED