@convext/cli 1.0.15 → 1.0.17

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.
@@ -0,0 +1,58 @@
1
+ export interface TelemetryEvent {
2
+ timestamp: string;
3
+ event_type: string;
4
+ source: string;
5
+ project_slug?: string;
6
+ rule_slug?: string;
7
+ rule_title?: string;
8
+ action?: string;
9
+ result?: 'blocked' | 'passed' | 'warned';
10
+ file?: string;
11
+ tool?: string;
12
+ payload?: Record<string, unknown>;
13
+ }
14
+ export interface TelemetrySummary {
15
+ total_events: number;
16
+ violations_blocked: number;
17
+ violations_warned: number;
18
+ compliance_checks: number;
19
+ tasks_completed: number;
20
+ by_rule: Record<string, {
21
+ blocked: number;
22
+ warned: number;
23
+ passed: number;
24
+ }>;
25
+ by_source: Record<string, number>;
26
+ by_day: Record<string, number>;
27
+ period_start?: string;
28
+ period_end?: string;
29
+ }
30
+ /**
31
+ * Log a telemetry event to the local JSONL file
32
+ */
33
+ export declare function logEvent(event: Omit<TelemetryEvent, 'timestamp'>, cwd?: string): void;
34
+ /**
35
+ * Read all events from the telemetry file
36
+ */
37
+ export declare function readEvents(cwd?: string): TelemetryEvent[];
38
+ /**
39
+ * Read events within a date range
40
+ */
41
+ export declare function readEventsInRange(startDate: Date, endDate: Date, cwd?: string): TelemetryEvent[];
42
+ /**
43
+ * Archive old events and clear the current telemetry file
44
+ */
45
+ export declare function rotateLog(cwd?: string): string | null;
46
+ /**
47
+ * Generate a summary of telemetry events
48
+ */
49
+ export declare function summarizeEvents(events: TelemetryEvent[]): TelemetrySummary;
50
+ /**
51
+ * Clear all telemetry data
52
+ */
53
+ export declare function clearTelemetry(cwd?: string): void;
54
+ /**
55
+ * Get the count of events in the telemetry file
56
+ */
57
+ export declare function getEventCount(cwd?: string): number;
58
+ //# sourceMappingURL=telemetry.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"telemetry.d.ts","sourceRoot":"","sources":["../../src/utils/telemetry.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,cAAc;IAC7B,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,EAAE,MAAM,CAAC;IACnB,MAAM,EAAE,MAAM,CAAC;IACf,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,SAAS,GAAG,QAAQ,GAAG,QAAQ,CAAC;IACzC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACnC;AAED,MAAM,WAAW,gBAAgB;IAC/B,YAAY,EAAE,MAAM,CAAC;IACrB,kBAAkB,EAAE,MAAM,CAAC;IAC3B,iBAAiB,EAAE,MAAM,CAAC;IAC1B,iBAAiB,EAAE,MAAM,CAAC;IAC1B,eAAe,EAAE,MAAM,CAAC;IACxB,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE;QAAE,OAAO,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IAC7E,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAClC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC/B,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAoBD;;GAEG;AACH,wBAAgB,QAAQ,CAAC,KAAK,EAAE,IAAI,CAAC,cAAc,EAAE,WAAW,CAAC,EAAE,GAAG,CAAC,EAAE,MAAM,GAAG,IAAI,CAUrF;AAED;;GAEG;AACH,wBAAgB,UAAU,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,cAAc,EAAE,CAiBzD;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAC/B,SAAS,EAAE,IAAI,EACf,OAAO,EAAE,IAAI,EACb,GAAG,CAAC,EAAE,MAAM,GACX,cAAc,EAAE,CAMlB;AAED;;GAEG;AACH,wBAAgB,SAAS,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAerD;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,MAAM,EAAE,cAAc,EAAE,GAAG,gBAAgB,CAgE1E;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,IAAI,CAKjD;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,CASlD"}
@@ -0,0 +1,156 @@
1
+ import { existsSync, readFileSync, writeFileSync, appendFileSync, renameSync, mkdirSync } from 'node:fs';
2
+ import { join, dirname } from 'node:path';
3
+ const TELEMETRY_DIR = '.convext';
4
+ const TELEMETRY_FILE = 'telemetry.jsonl';
5
+ const ARCHIVE_DIR = 'telemetry-archive';
6
+ function getTelemetryPath(cwd = process.cwd()) {
7
+ return join(cwd, TELEMETRY_DIR, TELEMETRY_FILE);
8
+ }
9
+ function getArchivePath(cwd = process.cwd()) {
10
+ return join(cwd, TELEMETRY_DIR, ARCHIVE_DIR);
11
+ }
12
+ function ensureDir(dirPath) {
13
+ if (!existsSync(dirPath)) {
14
+ mkdirSync(dirPath, { recursive: true });
15
+ }
16
+ }
17
+ /**
18
+ * Log a telemetry event to the local JSONL file
19
+ */
20
+ export function logEvent(event, cwd) {
21
+ const telemetryPath = getTelemetryPath(cwd);
22
+ ensureDir(dirname(telemetryPath));
23
+ const fullEvent = {
24
+ ...event,
25
+ timestamp: new Date().toISOString(),
26
+ };
27
+ appendFileSync(telemetryPath, JSON.stringify(fullEvent) + '\n', 'utf-8');
28
+ }
29
+ /**
30
+ * Read all events from the telemetry file
31
+ */
32
+ export function readEvents(cwd) {
33
+ const telemetryPath = getTelemetryPath(cwd);
34
+ if (!existsSync(telemetryPath)) {
35
+ return [];
36
+ }
37
+ const content = readFileSync(telemetryPath, 'utf-8');
38
+ const lines = content.trim().split('\n').filter(Boolean);
39
+ return lines.map((line) => {
40
+ try {
41
+ return JSON.parse(line);
42
+ }
43
+ catch {
44
+ return null;
45
+ }
46
+ }).filter((e) => e !== null);
47
+ }
48
+ /**
49
+ * Read events within a date range
50
+ */
51
+ export function readEventsInRange(startDate, endDate, cwd) {
52
+ const events = readEvents(cwd);
53
+ return events.filter((e) => {
54
+ const eventDate = new Date(e.timestamp);
55
+ return eventDate >= startDate && eventDate <= endDate;
56
+ });
57
+ }
58
+ /**
59
+ * Archive old events and clear the current telemetry file
60
+ */
61
+ export function rotateLog(cwd) {
62
+ const telemetryPath = getTelemetryPath(cwd);
63
+ if (!existsSync(telemetryPath)) {
64
+ return null;
65
+ }
66
+ const archiveDir = getArchivePath(cwd);
67
+ ensureDir(archiveDir);
68
+ const timestamp = new Date().toISOString().replace(/[:.]/g, '-');
69
+ const archiveFile = join(archiveDir, `telemetry-${timestamp}.jsonl`);
70
+ renameSync(telemetryPath, archiveFile);
71
+ return archiveFile;
72
+ }
73
+ /**
74
+ * Generate a summary of telemetry events
75
+ */
76
+ export function summarizeEvents(events) {
77
+ const summary = {
78
+ total_events: events.length,
79
+ violations_blocked: 0,
80
+ violations_warned: 0,
81
+ compliance_checks: 0,
82
+ tasks_completed: 0,
83
+ by_rule: {},
84
+ by_source: {},
85
+ by_day: {},
86
+ };
87
+ if (events.length === 0) {
88
+ return summary;
89
+ }
90
+ // Sort events by timestamp
91
+ const sorted = [...events].sort((a, b) => new Date(a.timestamp).getTime() - new Date(b.timestamp).getTime());
92
+ summary.period_start = sorted[0].timestamp;
93
+ summary.period_end = sorted[sorted.length - 1].timestamp;
94
+ for (const event of events) {
95
+ // Count by event type
96
+ if (event.event_type === 'violation') {
97
+ if (event.result === 'blocked') {
98
+ summary.violations_blocked++;
99
+ }
100
+ else if (event.result === 'warned') {
101
+ summary.violations_warned++;
102
+ }
103
+ }
104
+ else if (event.event_type === 'compliance_check') {
105
+ summary.compliance_checks++;
106
+ }
107
+ else if (event.event_type === 'task_complete') {
108
+ summary.tasks_completed++;
109
+ }
110
+ // Count by rule
111
+ const ruleKey = event.rule_title || event.rule_slug || 'unknown';
112
+ if (event.event_type === 'violation' && ruleKey !== 'unknown') {
113
+ if (!summary.by_rule[ruleKey]) {
114
+ summary.by_rule[ruleKey] = { blocked: 0, warned: 0, passed: 0 };
115
+ }
116
+ if (event.result === 'blocked') {
117
+ summary.by_rule[ruleKey].blocked++;
118
+ }
119
+ else if (event.result === 'warned') {
120
+ summary.by_rule[ruleKey].warned++;
121
+ }
122
+ else {
123
+ summary.by_rule[ruleKey].passed++;
124
+ }
125
+ }
126
+ // Count by source
127
+ if (event.source) {
128
+ summary.by_source[event.source] = (summary.by_source[event.source] || 0) + 1;
129
+ }
130
+ // Count by day
131
+ const day = event.timestamp.split('T')[0];
132
+ summary.by_day[day] = (summary.by_day[day] || 0) + 1;
133
+ }
134
+ return summary;
135
+ }
136
+ /**
137
+ * Clear all telemetry data
138
+ */
139
+ export function clearTelemetry(cwd) {
140
+ const telemetryPath = getTelemetryPath(cwd);
141
+ if (existsSync(telemetryPath)) {
142
+ writeFileSync(telemetryPath, '', 'utf-8');
143
+ }
144
+ }
145
+ /**
146
+ * Get the count of events in the telemetry file
147
+ */
148
+ export function getEventCount(cwd) {
149
+ const telemetryPath = getTelemetryPath(cwd);
150
+ if (!existsSync(telemetryPath)) {
151
+ return 0;
152
+ }
153
+ const content = readFileSync(telemetryPath, 'utf-8');
154
+ return content.trim().split('\n').filter(Boolean).length;
155
+ }
156
+ //# sourceMappingURL=telemetry.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"telemetry.js","sourceRoot":"","sources":["../../src/utils/telemetry.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@convext/cli",
3
- "version": "1.0.15",
3
+ "version": "1.0.17",
4
4
  "description": "CLI for Convext - sync engineering rules and standards to your project",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",