@boshu2/vibe-check 1.4.0 → 1.5.0
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/.vibe-check/sessions.json +11 -1
- package/PLAN-ultimate-game.md +1362 -0
- package/claude-progress.json +14 -8
- package/claude-progress.txt +53 -0
- package/dist/commands/profile.d.ts.map +1 -1
- package/dist/commands/profile.js +140 -31
- package/dist/commands/profile.js.map +1 -1
- package/dist/gamification/badges.d.ts +29 -0
- package/dist/gamification/badges.d.ts.map +1 -0
- package/dist/gamification/badges.js +114 -0
- package/dist/gamification/badges.js.map +1 -0
- package/dist/gamification/challenges.d.ts +42 -0
- package/dist/gamification/challenges.d.ts.map +1 -0
- package/dist/gamification/challenges.js +184 -0
- package/dist/gamification/challenges.js.map +1 -0
- package/dist/gamification/hall-of-fame.d.ts +17 -0
- package/dist/gamification/hall-of-fame.d.ts.map +1 -0
- package/dist/gamification/hall-of-fame.js +64 -0
- package/dist/gamification/hall-of-fame.js.map +1 -0
- package/dist/gamification/leaderboards.d.ts +49 -0
- package/dist/gamification/leaderboards.d.ts.map +1 -0
- package/dist/gamification/leaderboards.js +179 -0
- package/dist/gamification/leaderboards.js.map +1 -0
- package/dist/gamification/share.d.ts +29 -0
- package/dist/gamification/share.d.ts.map +1 -0
- package/dist/gamification/share.js +57 -0
- package/dist/gamification/share.js.map +1 -0
- package/dist/gamification/stats.d.ts +34 -0
- package/dist/gamification/stats.d.ts.map +1 -0
- package/dist/gamification/stats.js +91 -0
- package/dist/gamification/stats.js.map +1 -0
- package/dist/gamification/streaks.d.ts +9 -1
- package/dist/gamification/streaks.d.ts.map +1 -1
- package/dist/gamification/streaks.js +37 -4
- package/dist/gamification/streaks.js.map +1 -1
- package/dist/gamification/types.d.ts +35 -0
- package/dist/gamification/types.d.ts.map +1 -1
- package/dist/gamification/types.js +11 -3
- package/dist/gamification/types.js.map +1 -1
- package/dist/gamification/xp.d.ts +6 -2
- package/dist/gamification/xp.d.ts.map +1 -1
- package/dist/gamification/xp.js +27 -5
- package/dist/gamification/xp.js.map +1 -1
- package/dist/output/terminal.d.ts.map +1 -1
- package/dist/output/terminal.js +39 -0
- package/dist/output/terminal.js.map +1 -1
- package/feature-list.json +55 -1
- package/package.json +1 -1
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { UserProfile, SessionRecord, StreakState } from './types';
|
|
2
|
+
export type ChallengeType = 'TRUST_STREAK' | 'ZERO_SPIRALS' | 'ELITE_COUNT' | 'COMMIT_VOLUME' | 'STREAK_EXTEND';
|
|
3
|
+
export interface Challenge {
|
|
4
|
+
id: string;
|
|
5
|
+
type: ChallengeType;
|
|
6
|
+
name: string;
|
|
7
|
+
description: string;
|
|
8
|
+
icon: string;
|
|
9
|
+
target: number;
|
|
10
|
+
progress: number;
|
|
11
|
+
reward: number;
|
|
12
|
+
weekStart: string;
|
|
13
|
+
completed: boolean;
|
|
14
|
+
completedAt?: string;
|
|
15
|
+
}
|
|
16
|
+
export declare const CHALLENGE_DEFINITIONS: Record<ChallengeType, {
|
|
17
|
+
name: string;
|
|
18
|
+
description: (target: number) => string;
|
|
19
|
+
icon: string;
|
|
20
|
+
targets: number[];
|
|
21
|
+
rewards: number[];
|
|
22
|
+
}>;
|
|
23
|
+
/**
|
|
24
|
+
* Generate weekly challenges based on user's weak metrics
|
|
25
|
+
*/
|
|
26
|
+
export declare function generateWeeklyChallenges(profile: UserProfile): Challenge[];
|
|
27
|
+
/**
|
|
28
|
+
* Update challenge progress after a session
|
|
29
|
+
*/
|
|
30
|
+
export declare function updateChallengeProgress(challenges: Challenge[], session: SessionRecord, streak: StreakState): {
|
|
31
|
+
challenges: Challenge[];
|
|
32
|
+
completed: Challenge[];
|
|
33
|
+
};
|
|
34
|
+
/**
|
|
35
|
+
* Get current week's challenges, generating if needed
|
|
36
|
+
*/
|
|
37
|
+
export declare function getCurrentChallenges(profile: UserProfile): Challenge[];
|
|
38
|
+
/**
|
|
39
|
+
* Format challenges for display
|
|
40
|
+
*/
|
|
41
|
+
export declare function formatChallenges(challenges: Challenge[]): string;
|
|
42
|
+
//# sourceMappingURL=challenges.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"challenges.d.ts","sourceRoot":"","sources":["../../src/gamification/challenges.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,SAAS,CAAC;AAGlE,MAAM,MAAM,aAAa,GACrB,cAAc,GACd,cAAc,GACd,aAAa,GACb,eAAe,GACf,eAAe,CAAC;AAEpB,MAAM,WAAW,SAAS;IACxB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,aAAa,CAAC;IACpB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,MAAM,CAAC;IACf,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,OAAO,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,eAAO,MAAM,qBAAqB,EAAE,MAAM,CAAC,aAAa,EAAE;IACxD,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,MAAM,CAAC;IACxC,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,OAAO,EAAE,MAAM,EAAE,CAAC;CACnB,CAoCA,CAAC;AAEF;;GAEG;AACH,wBAAgB,wBAAwB,CAAC,OAAO,EAAE,WAAW,GAAG,SAAS,EAAE,CAyC1E;AAqBD;;GAEG;AACH,wBAAgB,uBAAuB,CACrC,UAAU,EAAE,SAAS,EAAE,EACvB,OAAO,EAAE,aAAa,EACtB,MAAM,EAAE,WAAW,GAClB;IAAE,UAAU,EAAE,SAAS,EAAE,CAAC;IAAC,SAAS,EAAE,SAAS,EAAE,CAAA;CAAE,CAgCrD;AAED;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,OAAO,EAAE,WAAW,GAAG,SAAS,EAAE,CAatE;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,UAAU,EAAE,SAAS,EAAE,GAAG,MAAM,CAUhE"}
|
|
@@ -0,0 +1,184 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.CHALLENGE_DEFINITIONS = void 0;
|
|
4
|
+
exports.generateWeeklyChallenges = generateWeeklyChallenges;
|
|
5
|
+
exports.updateChallengeProgress = updateChallengeProgress;
|
|
6
|
+
exports.getCurrentChallenges = getCurrentChallenges;
|
|
7
|
+
exports.formatChallenges = formatChallenges;
|
|
8
|
+
exports.CHALLENGE_DEFINITIONS = {
|
|
9
|
+
TRUST_STREAK: {
|
|
10
|
+
name: 'Trust Gauntlet',
|
|
11
|
+
description: (n) => `Get 90%+ trust in ${n} sessions`,
|
|
12
|
+
icon: '🎯',
|
|
13
|
+
targets: [3, 5, 7],
|
|
14
|
+
rewards: [50, 100, 150],
|
|
15
|
+
},
|
|
16
|
+
ZERO_SPIRALS: {
|
|
17
|
+
name: 'Zen Mode',
|
|
18
|
+
description: (n) => `${n} sessions with 0 spirals`,
|
|
19
|
+
icon: '🧘',
|
|
20
|
+
targets: [3, 5, 7],
|
|
21
|
+
rewards: [50, 100, 150],
|
|
22
|
+
},
|
|
23
|
+
ELITE_COUNT: {
|
|
24
|
+
name: 'Elite Streak',
|
|
25
|
+
description: (n) => `Get ${n} ELITE ratings this week`,
|
|
26
|
+
icon: '✨',
|
|
27
|
+
targets: [2, 4, 6],
|
|
28
|
+
rewards: [50, 100, 150],
|
|
29
|
+
},
|
|
30
|
+
COMMIT_VOLUME: {
|
|
31
|
+
name: 'Commit Champion',
|
|
32
|
+
description: (n) => `Analyze ${n}+ commits this week`,
|
|
33
|
+
icon: '📊',
|
|
34
|
+
targets: [50, 100, 200],
|
|
35
|
+
rewards: [30, 60, 100],
|
|
36
|
+
},
|
|
37
|
+
STREAK_EXTEND: {
|
|
38
|
+
name: 'Streak Builder',
|
|
39
|
+
description: (n) => `Extend your streak by ${n} days`,
|
|
40
|
+
icon: '🔥',
|
|
41
|
+
targets: [3, 5, 7],
|
|
42
|
+
rewards: [40, 80, 120],
|
|
43
|
+
},
|
|
44
|
+
};
|
|
45
|
+
/**
|
|
46
|
+
* Generate weekly challenges based on user's weak metrics
|
|
47
|
+
*/
|
|
48
|
+
function generateWeeklyChallenges(profile) {
|
|
49
|
+
const weekStart = getWeekStartISO(new Date());
|
|
50
|
+
const recentSessions = getSessionsThisWeek(profile.sessions, weekStart);
|
|
51
|
+
// Analyze weak areas
|
|
52
|
+
const avgTrust = recentSessions.length > 0
|
|
53
|
+
? recentSessions.reduce((sum, s) => sum + (s.vibeScore || 0), 0) / recentSessions.length
|
|
54
|
+
: 50;
|
|
55
|
+
const spiralCount = recentSessions.reduce((sum, s) => sum + s.spirals, 0);
|
|
56
|
+
const eliteCount = recentSessions.filter(s => s.overall === 'ELITE').length;
|
|
57
|
+
// Pick 3 challenges (1 based on weakness, 2 random)
|
|
58
|
+
const challenges = [];
|
|
59
|
+
const usedTypes = new Set();
|
|
60
|
+
// Challenge 1: Based on weakness
|
|
61
|
+
if (avgTrust < 80) {
|
|
62
|
+
challenges.push(createChallenge('TRUST_STREAK', weekStart, 1)); // Medium
|
|
63
|
+
usedTypes.add('TRUST_STREAK');
|
|
64
|
+
}
|
|
65
|
+
else if (spiralCount > 3) {
|
|
66
|
+
challenges.push(createChallenge('ZERO_SPIRALS', weekStart, 1));
|
|
67
|
+
usedTypes.add('ZERO_SPIRALS');
|
|
68
|
+
}
|
|
69
|
+
else if (eliteCount < 2) {
|
|
70
|
+
challenges.push(createChallenge('ELITE_COUNT', weekStart, 1));
|
|
71
|
+
usedTypes.add('ELITE_COUNT');
|
|
72
|
+
}
|
|
73
|
+
else {
|
|
74
|
+
challenges.push(createChallenge('STREAK_EXTEND', weekStart, 1));
|
|
75
|
+
usedTypes.add('STREAK_EXTEND');
|
|
76
|
+
}
|
|
77
|
+
// Challenge 2-3: Random from remaining
|
|
78
|
+
const remainingTypes = Object.keys(exports.CHALLENGE_DEFINITIONS)
|
|
79
|
+
.filter(t => !usedTypes.has(t));
|
|
80
|
+
for (let i = 0; i < 2 && remainingTypes.length > 0; i++) {
|
|
81
|
+
const idx = Math.floor(Math.random() * remainingTypes.length);
|
|
82
|
+
const type = remainingTypes.splice(idx, 1)[0];
|
|
83
|
+
challenges.push(createChallenge(type, weekStart, 0)); // Easy difficulty
|
|
84
|
+
}
|
|
85
|
+
return challenges;
|
|
86
|
+
}
|
|
87
|
+
function createChallenge(type, weekStart, difficultyIdx) {
|
|
88
|
+
const def = exports.CHALLENGE_DEFINITIONS[type];
|
|
89
|
+
const target = def.targets[difficultyIdx];
|
|
90
|
+
const reward = def.rewards[difficultyIdx];
|
|
91
|
+
return {
|
|
92
|
+
id: `${type}-${weekStart}`,
|
|
93
|
+
type,
|
|
94
|
+
name: def.name,
|
|
95
|
+
description: def.description(target),
|
|
96
|
+
icon: def.icon,
|
|
97
|
+
target,
|
|
98
|
+
progress: 0,
|
|
99
|
+
reward,
|
|
100
|
+
weekStart,
|
|
101
|
+
completed: false,
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
/**
|
|
105
|
+
* Update challenge progress after a session
|
|
106
|
+
*/
|
|
107
|
+
function updateChallengeProgress(challenges, session, streak) {
|
|
108
|
+
const completed = [];
|
|
109
|
+
for (const challenge of challenges) {
|
|
110
|
+
if (challenge.completed)
|
|
111
|
+
continue;
|
|
112
|
+
switch (challenge.type) {
|
|
113
|
+
case 'TRUST_STREAK':
|
|
114
|
+
if (session.vibeScore >= 90)
|
|
115
|
+
challenge.progress++;
|
|
116
|
+
break;
|
|
117
|
+
case 'ZERO_SPIRALS':
|
|
118
|
+
if (session.spirals === 0 && session.commits >= 10)
|
|
119
|
+
challenge.progress++;
|
|
120
|
+
break;
|
|
121
|
+
case 'ELITE_COUNT':
|
|
122
|
+
if (session.overall === 'ELITE')
|
|
123
|
+
challenge.progress++;
|
|
124
|
+
break;
|
|
125
|
+
case 'COMMIT_VOLUME':
|
|
126
|
+
challenge.progress += session.commits;
|
|
127
|
+
break;
|
|
128
|
+
case 'STREAK_EXTEND':
|
|
129
|
+
challenge.progress = streak.current - (challenge.progress || 0);
|
|
130
|
+
break;
|
|
131
|
+
}
|
|
132
|
+
if (challenge.progress >= challenge.target) {
|
|
133
|
+
challenge.completed = true;
|
|
134
|
+
challenge.completedAt = new Date().toISOString();
|
|
135
|
+
completed.push(challenge);
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
return { challenges, completed };
|
|
139
|
+
}
|
|
140
|
+
/**
|
|
141
|
+
* Get current week's challenges, generating if needed
|
|
142
|
+
*/
|
|
143
|
+
function getCurrentChallenges(profile) {
|
|
144
|
+
const weekStart = getWeekStartISO(new Date());
|
|
145
|
+
const existingChallenges = profile.challenges || [];
|
|
146
|
+
// Check if we have challenges for this week
|
|
147
|
+
const thisWeekChallenges = existingChallenges.filter(c => c.weekStart === weekStart);
|
|
148
|
+
if (thisWeekChallenges.length >= 3) {
|
|
149
|
+
return thisWeekChallenges;
|
|
150
|
+
}
|
|
151
|
+
// Generate new challenges
|
|
152
|
+
return generateWeeklyChallenges(profile);
|
|
153
|
+
}
|
|
154
|
+
/**
|
|
155
|
+
* Format challenges for display
|
|
156
|
+
*/
|
|
157
|
+
function formatChallenges(challenges) {
|
|
158
|
+
const lines = [];
|
|
159
|
+
for (const c of challenges) {
|
|
160
|
+
const progressBar = createProgressBar(c.progress, c.target, 10);
|
|
161
|
+
const status = c.completed ? '✓ COMPLETE' : `${c.progress}/${c.target}`;
|
|
162
|
+
lines.push(`${c.icon} ${c.name}: ${progressBar} ${status}`);
|
|
163
|
+
}
|
|
164
|
+
return lines.join('\n');
|
|
165
|
+
}
|
|
166
|
+
function createProgressBar(current, total, length) {
|
|
167
|
+
const pct = Math.min(current / total, 1);
|
|
168
|
+
const filled = Math.round(pct * length);
|
|
169
|
+
const empty = length - filled;
|
|
170
|
+
return '█'.repeat(filled) + '░'.repeat(empty);
|
|
171
|
+
}
|
|
172
|
+
function getWeekStartISO(date) {
|
|
173
|
+
const d = new Date(date);
|
|
174
|
+
const day = d.getDay();
|
|
175
|
+
const diff = d.getDate() - day + (day === 0 ? -6 : 1);
|
|
176
|
+
d.setDate(diff);
|
|
177
|
+
d.setHours(0, 0, 0, 0);
|
|
178
|
+
return d.toISOString().split('T')[0];
|
|
179
|
+
}
|
|
180
|
+
function getSessionsThisWeek(sessions, weekStart) {
|
|
181
|
+
const start = new Date(weekStart);
|
|
182
|
+
return sessions.filter(s => new Date(s.date) >= start);
|
|
183
|
+
}
|
|
184
|
+
//# sourceMappingURL=challenges.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"challenges.js","sourceRoot":"","sources":["../../src/gamification/challenges.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { Leaderboards } from './leaderboards';
|
|
2
|
+
export interface HallOfFameRecord {
|
|
3
|
+
category: string;
|
|
4
|
+
icon: string;
|
|
5
|
+
value: string;
|
|
6
|
+
date: string;
|
|
7
|
+
context: string;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* Get Hall of Fame records from leaderboards
|
|
11
|
+
*/
|
|
12
|
+
export declare function getHallOfFame(leaderboards: Leaderboards): HallOfFameRecord[];
|
|
13
|
+
/**
|
|
14
|
+
* Format Hall of Fame for display
|
|
15
|
+
*/
|
|
16
|
+
export declare function formatHallOfFame(records: HallOfFameRecord[]): string;
|
|
17
|
+
//# sourceMappingURL=hall-of-fame.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"hall-of-fame.d.ts","sourceRoot":"","sources":["../../src/gamification/hall-of-fame.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAE9C,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;CACjB;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,YAAY,EAAE,YAAY,GAAG,gBAAgB,EAAE,CA6C5E;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,gBAAgB,EAAE,GAAG,MAAM,CAcpE"}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getHallOfFame = getHallOfFame;
|
|
4
|
+
exports.formatHallOfFame = formatHallOfFame;
|
|
5
|
+
/**
|
|
6
|
+
* Get Hall of Fame records from leaderboards
|
|
7
|
+
*/
|
|
8
|
+
function getHallOfFame(leaderboards) {
|
|
9
|
+
const records = [];
|
|
10
|
+
const pb = leaderboards.personalBests;
|
|
11
|
+
if (pb.highestScore) {
|
|
12
|
+
records.push({
|
|
13
|
+
category: 'Best Vibe Score',
|
|
14
|
+
icon: '🏆',
|
|
15
|
+
value: `${pb.highestScore.vibeScore}%`,
|
|
16
|
+
date: pb.highestScore.date,
|
|
17
|
+
context: `${pb.highestScore.repoName} - ${pb.highestScore.overall}`,
|
|
18
|
+
});
|
|
19
|
+
}
|
|
20
|
+
if (pb.longestStreak > 0) {
|
|
21
|
+
records.push({
|
|
22
|
+
category: 'Longest Streak',
|
|
23
|
+
icon: '🔥',
|
|
24
|
+
value: `${pb.longestStreak} days`,
|
|
25
|
+
date: 'All time',
|
|
26
|
+
context: 'Consecutive daily check-ins',
|
|
27
|
+
});
|
|
28
|
+
}
|
|
29
|
+
if (pb.bestWeekXP) {
|
|
30
|
+
records.push({
|
|
31
|
+
category: 'Best Week XP',
|
|
32
|
+
icon: '⚡',
|
|
33
|
+
value: `${pb.bestWeekXP.xp} XP`,
|
|
34
|
+
date: pb.bestWeekXP.week,
|
|
35
|
+
context: 'Most XP earned in a single week',
|
|
36
|
+
});
|
|
37
|
+
}
|
|
38
|
+
if (pb.mostCommits) {
|
|
39
|
+
records.push({
|
|
40
|
+
category: 'Most Commits',
|
|
41
|
+
icon: '📊',
|
|
42
|
+
value: `${pb.mostCommits.commits}`,
|
|
43
|
+
date: pb.mostCommits.date,
|
|
44
|
+
context: `${pb.mostCommits.repoName} - single session`,
|
|
45
|
+
});
|
|
46
|
+
}
|
|
47
|
+
return records;
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Format Hall of Fame for display
|
|
51
|
+
*/
|
|
52
|
+
function formatHallOfFame(records) {
|
|
53
|
+
if (records.length === 0) {
|
|
54
|
+
return 'No records yet. Keep coding!';
|
|
55
|
+
}
|
|
56
|
+
const lines = ['🏛️ HALL OF FAME', ''];
|
|
57
|
+
for (const record of records) {
|
|
58
|
+
lines.push(`${record.icon} ${record.category}: ${record.value}`);
|
|
59
|
+
lines.push(` ${record.date} - ${record.context}`);
|
|
60
|
+
lines.push('');
|
|
61
|
+
}
|
|
62
|
+
return lines.join('\n');
|
|
63
|
+
}
|
|
64
|
+
//# sourceMappingURL=hall-of-fame.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"hall-of-fame.js","sourceRoot":"","sources":["../../src/gamification/hall-of-fame.ts"],"names":[],"mappings":";;AAaA,sCA6CC;AAKD,4CAcC;AAnED;;GAEG;AACH,SAAgB,aAAa,CAAC,YAA0B;IACtD,MAAM,OAAO,GAAuB,EAAE,CAAC;IACvC,MAAM,EAAE,GAAG,YAAY,CAAC,aAAa,CAAC;IAEtC,IAAI,EAAE,CAAC,YAAY,EAAE,CAAC;QACpB,OAAO,CAAC,IAAI,CAAC;YACX,QAAQ,EAAE,iBAAiB;YAC3B,IAAI,EAAE,IAAI;YACV,KAAK,EAAE,GAAG,EAAE,CAAC,YAAY,CAAC,SAAS,GAAG;YACtC,IAAI,EAAE,EAAE,CAAC,YAAY,CAAC,IAAI;YAC1B,OAAO,EAAE,GAAG,EAAE,CAAC,YAAY,CAAC,QAAQ,MAAM,EAAE,CAAC,YAAY,CAAC,OAAO,EAAE;SACpE,CAAC,CAAC;IACL,CAAC;IAED,IAAI,EAAE,CAAC,aAAa,GAAG,CAAC,EAAE,CAAC;QACzB,OAAO,CAAC,IAAI,CAAC;YACX,QAAQ,EAAE,gBAAgB;YAC1B,IAAI,EAAE,IAAI;YACV,KAAK,EAAE,GAAG,EAAE,CAAC,aAAa,OAAO;YACjC,IAAI,EAAE,UAAU;YAChB,OAAO,EAAE,6BAA6B;SACvC,CAAC,CAAC;IACL,CAAC;IAED,IAAI,EAAE,CAAC,UAAU,EAAE,CAAC;QAClB,OAAO,CAAC,IAAI,CAAC;YACX,QAAQ,EAAE,cAAc;YACxB,IAAI,EAAE,GAAG;YACT,KAAK,EAAE,GAAG,EAAE,CAAC,UAAU,CAAC,EAAE,KAAK;YAC/B,IAAI,EAAE,EAAE,CAAC,UAAU,CAAC,IAAI;YACxB,OAAO,EAAE,iCAAiC;SAC3C,CAAC,CAAC;IACL,CAAC;IAED,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC;QACnB,OAAO,CAAC,IAAI,CAAC;YACX,QAAQ,EAAE,cAAc;YACxB,IAAI,EAAE,IAAI;YACV,KAAK,EAAE,GAAG,EAAE,CAAC,WAAW,CAAC,OAAO,EAAE;YAClC,IAAI,EAAE,EAAE,CAAC,WAAW,CAAC,IAAI;YACzB,OAAO,EAAE,GAAG,EAAE,CAAC,WAAW,CAAC,QAAQ,mBAAmB;SACvD,CAAC,CAAC;IACL,CAAC;IAED,OAAO,OAAO,CAAC;AACjB,CAAC;AAED;;GAEG;AACH,SAAgB,gBAAgB,CAAC,OAA2B;IAC1D,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACzB,OAAO,8BAA8B,CAAC;IACxC,CAAC;IAED,MAAM,KAAK,GAAa,CAAC,mBAAmB,EAAE,EAAE,CAAC,CAAC;IAElD,KAAK,MAAM,MAAM,IAAI,OAAO,EAAE,CAAC;QAC7B,KAAK,CAAC,IAAI,CAAC,GAAG,MAAM,CAAC,IAAI,IAAI,MAAM,CAAC,QAAQ,KAAK,MAAM,CAAC,KAAK,EAAE,CAAC,CAAC;QACjE,KAAK,CAAC,IAAI,CAAC,MAAM,MAAM,CAAC,IAAI,MAAM,MAAM,CAAC,OAAO,EAAE,CAAC,CAAC;QACpD,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IACjB,CAAC;IAED,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAC1B,CAAC"}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { SessionRecord } from './types';
|
|
2
|
+
export interface LeaderboardEntry {
|
|
3
|
+
date: string;
|
|
4
|
+
repoPath: string;
|
|
5
|
+
repoName: string;
|
|
6
|
+
vibeScore: number;
|
|
7
|
+
overall: string;
|
|
8
|
+
commits: number;
|
|
9
|
+
xpEarned: number;
|
|
10
|
+
}
|
|
11
|
+
export interface Leaderboards {
|
|
12
|
+
version: string;
|
|
13
|
+
entries: LeaderboardEntry[];
|
|
14
|
+
byRepo: Record<string, LeaderboardEntry[]>;
|
|
15
|
+
personalBests: {
|
|
16
|
+
highestScore: LeaderboardEntry | null;
|
|
17
|
+
longestStreak: number;
|
|
18
|
+
bestWeekXP: {
|
|
19
|
+
week: string;
|
|
20
|
+
xp: number;
|
|
21
|
+
} | null;
|
|
22
|
+
mostCommits: LeaderboardEntry | null;
|
|
23
|
+
};
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Get leaderboards file path
|
|
27
|
+
*/
|
|
28
|
+
export declare function getLeaderboardsPath(): string;
|
|
29
|
+
/**
|
|
30
|
+
* Load leaderboards from disk
|
|
31
|
+
*/
|
|
32
|
+
export declare function loadLeaderboards(): Leaderboards;
|
|
33
|
+
/**
|
|
34
|
+
* Save leaderboards to disk
|
|
35
|
+
*/
|
|
36
|
+
export declare function saveLeaderboards(leaderboards: Leaderboards): void;
|
|
37
|
+
/**
|
|
38
|
+
* Create initial leaderboards
|
|
39
|
+
*/
|
|
40
|
+
export declare function createInitialLeaderboards(): Leaderboards;
|
|
41
|
+
/**
|
|
42
|
+
* Record a session to leaderboards
|
|
43
|
+
*/
|
|
44
|
+
export declare function recordToLeaderboard(session: SessionRecord, repoPath: string, xpEarned: number, streak: number): Leaderboards;
|
|
45
|
+
/**
|
|
46
|
+
* Format leaderboard for display
|
|
47
|
+
*/
|
|
48
|
+
export declare function formatLeaderboard(leaderboards: Leaderboards, repoPath?: string): string;
|
|
49
|
+
//# sourceMappingURL=leaderboards.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"leaderboards.d.ts","sourceRoot":"","sources":["../../src/gamification/leaderboards.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,aAAa,EAAE,MAAM,SAAS,CAAC;AAIxC,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,YAAY;IAC3B,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,gBAAgB,EAAE,CAAC;IAC5B,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,gBAAgB,EAAE,CAAC,CAAC;IAC3C,aAAa,EAAE;QACb,YAAY,EAAE,gBAAgB,GAAG,IAAI,CAAC;QACtC,aAAa,EAAE,MAAM,CAAC;QACtB,UAAU,EAAE;YAAE,IAAI,EAAE,MAAM,CAAC;YAAC,EAAE,EAAE,MAAM,CAAA;SAAE,GAAG,IAAI,CAAC;QAChD,WAAW,EAAE,gBAAgB,GAAG,IAAI,CAAC;KACtC,CAAC;CACH;AAED;;GAEG;AACH,wBAAgB,mBAAmB,IAAI,MAAM,CAE5C;AAED;;GAEG;AACH,wBAAgB,gBAAgB,IAAI,YAAY,CAY/C;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,YAAY,EAAE,YAAY,GAAG,IAAI,CASjE;AAED;;GAEG;AACH,wBAAgB,yBAAyB,IAAI,YAAY,CAYxD;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CACjC,OAAO,EAAE,aAAa,EACtB,QAAQ,EAAE,MAAM,EAChB,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,GACb,YAAY,CAuDd;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,YAAY,EAAE,YAAY,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,MAAM,CAyBvF"}
|
|
@@ -0,0 +1,179 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
exports.getLeaderboardsPath = getLeaderboardsPath;
|
|
37
|
+
exports.loadLeaderboards = loadLeaderboards;
|
|
38
|
+
exports.saveLeaderboards = saveLeaderboards;
|
|
39
|
+
exports.createInitialLeaderboards = createInitialLeaderboards;
|
|
40
|
+
exports.recordToLeaderboard = recordToLeaderboard;
|
|
41
|
+
exports.formatLeaderboard = formatLeaderboard;
|
|
42
|
+
const fs = __importStar(require("fs"));
|
|
43
|
+
const path = __importStar(require("path"));
|
|
44
|
+
const os = __importStar(require("os"));
|
|
45
|
+
const LEADERBOARD_FILE = 'leaderboards.json';
|
|
46
|
+
/**
|
|
47
|
+
* Get leaderboards file path
|
|
48
|
+
*/
|
|
49
|
+
function getLeaderboardsPath() {
|
|
50
|
+
return path.join(os.homedir(), '.vibe-check', LEADERBOARD_FILE);
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Load leaderboards from disk
|
|
54
|
+
*/
|
|
55
|
+
function loadLeaderboards() {
|
|
56
|
+
const filePath = getLeaderboardsPath();
|
|
57
|
+
if (fs.existsSync(filePath)) {
|
|
58
|
+
try {
|
|
59
|
+
return JSON.parse(fs.readFileSync(filePath, 'utf-8'));
|
|
60
|
+
}
|
|
61
|
+
catch {
|
|
62
|
+
return createInitialLeaderboards();
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
return createInitialLeaderboards();
|
|
66
|
+
}
|
|
67
|
+
/**
|
|
68
|
+
* Save leaderboards to disk
|
|
69
|
+
*/
|
|
70
|
+
function saveLeaderboards(leaderboards) {
|
|
71
|
+
const filePath = getLeaderboardsPath();
|
|
72
|
+
const dir = path.dirname(filePath);
|
|
73
|
+
if (!fs.existsSync(dir)) {
|
|
74
|
+
fs.mkdirSync(dir, { recursive: true });
|
|
75
|
+
}
|
|
76
|
+
fs.writeFileSync(filePath, JSON.stringify(leaderboards, null, 2));
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Create initial leaderboards
|
|
80
|
+
*/
|
|
81
|
+
function createInitialLeaderboards() {
|
|
82
|
+
return {
|
|
83
|
+
version: '1.0.0',
|
|
84
|
+
entries: [],
|
|
85
|
+
byRepo: {},
|
|
86
|
+
personalBests: {
|
|
87
|
+
highestScore: null,
|
|
88
|
+
longestStreak: 0,
|
|
89
|
+
bestWeekXP: null,
|
|
90
|
+
mostCommits: null,
|
|
91
|
+
},
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
/**
|
|
95
|
+
* Record a session to leaderboards
|
|
96
|
+
*/
|
|
97
|
+
function recordToLeaderboard(session, repoPath, xpEarned, streak) {
|
|
98
|
+
const leaderboards = loadLeaderboards();
|
|
99
|
+
const repoName = path.basename(repoPath);
|
|
100
|
+
const entry = {
|
|
101
|
+
date: session.date,
|
|
102
|
+
repoPath,
|
|
103
|
+
repoName,
|
|
104
|
+
vibeScore: session.vibeScore,
|
|
105
|
+
overall: session.overall,
|
|
106
|
+
commits: session.commits,
|
|
107
|
+
xpEarned,
|
|
108
|
+
};
|
|
109
|
+
// Add to global entries (sorted by score, top 100)
|
|
110
|
+
leaderboards.entries.push(entry);
|
|
111
|
+
leaderboards.entries.sort((a, b) => b.vibeScore - a.vibeScore);
|
|
112
|
+
leaderboards.entries = leaderboards.entries.slice(0, 100);
|
|
113
|
+
// Add to repo-specific entries (top 10)
|
|
114
|
+
if (!leaderboards.byRepo[repoPath]) {
|
|
115
|
+
leaderboards.byRepo[repoPath] = [];
|
|
116
|
+
}
|
|
117
|
+
leaderboards.byRepo[repoPath].push(entry);
|
|
118
|
+
leaderboards.byRepo[repoPath].sort((a, b) => b.vibeScore - a.vibeScore);
|
|
119
|
+
leaderboards.byRepo[repoPath] = leaderboards.byRepo[repoPath].slice(0, 10);
|
|
120
|
+
// Update personal bests
|
|
121
|
+
if (!leaderboards.personalBests.highestScore ||
|
|
122
|
+
session.vibeScore > leaderboards.personalBests.highestScore.vibeScore) {
|
|
123
|
+
leaderboards.personalBests.highestScore = entry;
|
|
124
|
+
}
|
|
125
|
+
if (streak > leaderboards.personalBests.longestStreak) {
|
|
126
|
+
leaderboards.personalBests.longestStreak = streak;
|
|
127
|
+
}
|
|
128
|
+
if (!leaderboards.personalBests.mostCommits ||
|
|
129
|
+
session.commits > leaderboards.personalBests.mostCommits.commits) {
|
|
130
|
+
leaderboards.personalBests.mostCommits = entry;
|
|
131
|
+
}
|
|
132
|
+
// Track weekly XP
|
|
133
|
+
const weekStart = getWeekStartISO(new Date(session.date));
|
|
134
|
+
const currentWeekXP = leaderboards.personalBests.bestWeekXP;
|
|
135
|
+
if (!currentWeekXP || currentWeekXP.week !== weekStart) {
|
|
136
|
+
// New week - check if we beat previous best
|
|
137
|
+
// (simplified - in practice would need to sum week's XP)
|
|
138
|
+
leaderboards.personalBests.bestWeekXP = { week: weekStart, xp: xpEarned };
|
|
139
|
+
}
|
|
140
|
+
else {
|
|
141
|
+
currentWeekXP.xp += xpEarned;
|
|
142
|
+
}
|
|
143
|
+
saveLeaderboards(leaderboards);
|
|
144
|
+
return leaderboards;
|
|
145
|
+
}
|
|
146
|
+
/**
|
|
147
|
+
* Format leaderboard for display
|
|
148
|
+
*/
|
|
149
|
+
function formatLeaderboard(leaderboards, repoPath) {
|
|
150
|
+
const lines = [];
|
|
151
|
+
if (repoPath && leaderboards.byRepo[repoPath]) {
|
|
152
|
+
const repoEntries = leaderboards.byRepo[repoPath];
|
|
153
|
+
lines.push(`📊 Top Scores - ${path.basename(repoPath)}`);
|
|
154
|
+
lines.push('');
|
|
155
|
+
for (let i = 0; i < Math.min(repoEntries.length, 5); i++) {
|
|
156
|
+
const e = repoEntries[i];
|
|
157
|
+
const medal = i === 0 ? '🥇' : i === 1 ? '🥈' : i === 2 ? '🥉' : ' ';
|
|
158
|
+
lines.push(`${medal} ${e.vibeScore}% ${e.overall.padEnd(6)} ${e.date}`);
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
else {
|
|
162
|
+
lines.push('🏆 All-Time Top Scores');
|
|
163
|
+
lines.push('');
|
|
164
|
+
for (let i = 0; i < Math.min(leaderboards.entries.length, 10); i++) {
|
|
165
|
+
const e = leaderboards.entries[i];
|
|
166
|
+
const medal = i === 0 ? '🥇' : i === 1 ? '🥈' : i === 2 ? '🥉' : `${i + 1}.`;
|
|
167
|
+
lines.push(`${medal} ${e.vibeScore}% ${e.overall.padEnd(6)} ${e.repoName} (${e.date})`);
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
return lines.join('\n');
|
|
171
|
+
}
|
|
172
|
+
function getWeekStartISO(date) {
|
|
173
|
+
const d = new Date(date);
|
|
174
|
+
const day = d.getDay();
|
|
175
|
+
const diff = d.getDate() - day + (day === 0 ? -6 : 1);
|
|
176
|
+
d.setDate(diff);
|
|
177
|
+
return d.toISOString().split('T')[0];
|
|
178
|
+
}
|
|
179
|
+
//# sourceMappingURL=leaderboards.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"leaderboards.js","sourceRoot":"","sources":["../../src/gamification/leaderboards.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { UserProfile } from './types';
|
|
2
|
+
export interface ShareableProfile {
|
|
3
|
+
username?: string;
|
|
4
|
+
level: number;
|
|
5
|
+
levelName: string;
|
|
6
|
+
totalXP: number;
|
|
7
|
+
badge: string | null;
|
|
8
|
+
streak: number;
|
|
9
|
+
longestStreak: number;
|
|
10
|
+
totalSessions: number;
|
|
11
|
+
avgScore: number;
|
|
12
|
+
bestScore: number;
|
|
13
|
+
achievementCount: number;
|
|
14
|
+
prestigeTier?: number;
|
|
15
|
+
generatedAt: string;
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Create shareable profile data
|
|
19
|
+
*/
|
|
20
|
+
export declare function createShareableProfile(profile: UserProfile, username?: string): ShareableProfile;
|
|
21
|
+
/**
|
|
22
|
+
* Format profile for sharing (text format)
|
|
23
|
+
*/
|
|
24
|
+
export declare function formatShareText(shareable: ShareableProfile): string;
|
|
25
|
+
/**
|
|
26
|
+
* Format profile as JSON for clipboard
|
|
27
|
+
*/
|
|
28
|
+
export declare function formatShareJSON(shareable: ShareableProfile): string;
|
|
29
|
+
//# sourceMappingURL=share.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"share.d.ts","sourceRoot":"","sources":["../../src/gamification/share.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAkB,MAAM,SAAS,CAAC;AAGtD,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,MAAM,CAAC;IAChB,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;IACrB,MAAM,EAAE,MAAM,CAAC;IACf,aAAa,EAAE,MAAM,CAAC;IACtB,aAAa,EAAE,MAAM,CAAC;IACtB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,CAAC;IAClB,gBAAgB,EAAE,MAAM,CAAC;IACzB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,EAAE,MAAM,CAAC;CACrB;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CACpC,OAAO,EAAE,WAAW,EACpB,QAAQ,CAAC,EAAE,MAAM,GAChB,gBAAgB,CAsBlB;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,SAAS,EAAE,gBAAgB,GAAG,MAAM,CAqBnE;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,SAAS,EAAE,gBAAgB,GAAG,MAAM,CAEnE"}
|