vibecodingmachine-core 1.0.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.
Files changed (54) hide show
  1. package/.babelrc +13 -0
  2. package/README.md +28 -0
  3. package/__tests__/applescript-manager-claude-fix.test.js +286 -0
  4. package/__tests__/requirement-2-auto-start-looping.test.js +69 -0
  5. package/__tests__/requirement-3-auto-start-looping.test.js +69 -0
  6. package/__tests__/requirement-4-auto-start-looping.test.js +69 -0
  7. package/__tests__/requirement-6-auto-start-looping.test.js +73 -0
  8. package/__tests__/requirement-7-status-tracking.test.js +332 -0
  9. package/jest.config.js +18 -0
  10. package/jest.setup.js +12 -0
  11. package/package.json +46 -0
  12. package/src/auth/access-denied.html +119 -0
  13. package/src/auth/shared-auth-storage.js +230 -0
  14. package/src/autonomous-mode/feature-implementer.cjs +70 -0
  15. package/src/autonomous-mode/feature-implementer.js +425 -0
  16. package/src/chat-management/chat-manager.cjs +71 -0
  17. package/src/chat-management/chat-manager.js +342 -0
  18. package/src/ide-integration/__tests__/applescript-manager-thread-closure.test.js +227 -0
  19. package/src/ide-integration/aider-cli-manager.cjs +850 -0
  20. package/src/ide-integration/applescript-diagnostics.js +0 -0
  21. package/src/ide-integration/applescript-manager.cjs +1088 -0
  22. package/src/ide-integration/applescript-manager.js +2803 -0
  23. package/src/ide-integration/applescript-open-apps.js +0 -0
  24. package/src/ide-integration/applescript-read-response.js +0 -0
  25. package/src/ide-integration/applescript-send-text.js +0 -0
  26. package/src/ide-integration/applescript-thread-closure.js +0 -0
  27. package/src/ide-integration/applescript-utils.js +306 -0
  28. package/src/ide-integration/cdp-manager.cjs +221 -0
  29. package/src/ide-integration/cdp-manager.js +321 -0
  30. package/src/ide-integration/claude-code-cli-manager.cjs +301 -0
  31. package/src/ide-integration/cline-cli-manager.cjs +2252 -0
  32. package/src/ide-integration/continue-cli-manager.js +431 -0
  33. package/src/ide-integration/provider-manager.cjs +354 -0
  34. package/src/ide-integration/quota-detector.cjs +34 -0
  35. package/src/ide-integration/quota-detector.js +349 -0
  36. package/src/ide-integration/windows-automation-manager.js +262 -0
  37. package/src/index.cjs +43 -0
  38. package/src/index.js +17 -0
  39. package/src/llm/direct-llm-manager.cjs +609 -0
  40. package/src/ui/ButtonComponents.js +247 -0
  41. package/src/ui/ChatInterface.js +499 -0
  42. package/src/ui/StateManager.js +259 -0
  43. package/src/ui/StateManager.test.js +0 -0
  44. package/src/utils/audit-logger.cjs +116 -0
  45. package/src/utils/config-helpers.cjs +94 -0
  46. package/src/utils/config-helpers.js +94 -0
  47. package/src/utils/electron-update-checker.js +78 -0
  48. package/src/utils/gcloud-auth.cjs +394 -0
  49. package/src/utils/logger.cjs +193 -0
  50. package/src/utils/logger.js +191 -0
  51. package/src/utils/repo-helpers.cjs +120 -0
  52. package/src/utils/repo-helpers.js +120 -0
  53. package/src/utils/requirement-helpers.js +432 -0
  54. package/src/utils/update-checker.js +167 -0
@@ -0,0 +1,332 @@
1
+ /**
2
+ * Test suite for Requirement 7: Status tracking and logging improvements
3
+ *
4
+ * This test verifies that the file watcher properly tracks status changes
5
+ * and only logs requirement completion when status changes from "IN PROGRESS" to "DONE"
6
+ */
7
+
8
+ const fs = require('fs');
9
+ const path = require('path');
10
+
11
+ describe('Requirement 7: Status Tracking and Logging', () => {
12
+ let mockRequirementsContent;
13
+ let mockFilePath;
14
+ let mockMainWindow;
15
+ let consoleSpy;
16
+
17
+ beforeEach(() => {
18
+ // Mock console methods to capture logs
19
+ consoleSpy = {
20
+ log: jest.spyOn(console, 'log').mockImplementation(() => {}),
21
+ error: jest.spyOn(console, 'error').mockImplementation(() => {})
22
+ };
23
+
24
+ // Mock file system
25
+ jest.spyOn(fs, 'readFileSync').mockImplementation((filePath) => {
26
+ if (filePath === mockFilePath) {
27
+ return mockRequirementsContent;
28
+ }
29
+ return '';
30
+ });
31
+
32
+ jest.spyOn(fs, 'existsSync').mockReturnValue(true);
33
+
34
+ // Mock main window
35
+ mockMainWindow = {
36
+ isDestroyed: jest.fn().mockReturnValue(false),
37
+ webContents: {
38
+ send: jest.fn()
39
+ }
40
+ };
41
+
42
+ mockFilePath = '/test/requirements.md';
43
+ });
44
+
45
+ afterEach(() => {
46
+ jest.restoreAllMocks();
47
+ });
48
+
49
+ describe('Status Parsing Functions', () => {
50
+ test('parseCurrentStatus should extract status from Current Status section', () => {
51
+ // Import the function (we'll need to mock the module)
52
+ const { parseCurrentStatus } = require('../../electron-app/src/main/file-watcher');
53
+
54
+ const content = `
55
+ # Requirements
56
+
57
+ ## 🚦 Current Status
58
+
59
+ IN PROGRESS
60
+
61
+ ## Other Section
62
+ Some other content
63
+ `;
64
+
65
+ const status = parseCurrentStatus(content);
66
+ expect(status).toBe('IN PROGRESS');
67
+ });
68
+
69
+ test('parseCurrentStatus should handle empty status section', () => {
70
+ const { parseCurrentStatus } = require('../../electron-app/src/main/file-watcher');
71
+
72
+ const content = `
73
+ # Requirements
74
+
75
+ ## 🚦 Current Status
76
+
77
+ ## Other Section
78
+ Some other content
79
+ `;
80
+
81
+ const status = parseCurrentStatus(content);
82
+ expect(status).toBe('');
83
+ });
84
+
85
+ test('extractCurrentRequirementDetails should extract requirement from Current In Progress section', () => {
86
+ const { extractCurrentRequirementDetails } = require('../../electron-app/src/main/file-watcher');
87
+
88
+ const content = `
89
+ # Requirements
90
+
91
+ ## 🔨 Current In Progress Requirement
92
+
93
+ 7: Update PROCESSES.md and the electron app if needed so that when the electron app is watching for REQUIREMENTS file updates, it does not log that a requirement was done until it is done, at which time the REQUIREMENT file "Current Status" changes from "IN PROGRESS" to "DONE".
94
+
95
+ ## Other Section
96
+ Some other content
97
+ `;
98
+
99
+ const details = extractCurrentRequirementDetails(content);
100
+ expect(details).toContain('7: Update PROCESSES.md');
101
+ expect(details).toContain('IN PROGRESS');
102
+ expect(details).toContain('DONE');
103
+ });
104
+ });
105
+
106
+ describe('Status Change Detection', () => {
107
+ test('should log requirement completion when status changes from IN PROGRESS to DONE', () => {
108
+ const { handleRequirementsFileChange } = require('../../electron-app/src/main/file-watcher');
109
+
110
+ // First call - IN PROGRESS status
111
+ mockRequirementsContent = `
112
+ # Requirements
113
+
114
+ ## 🚦 Current Status
115
+
116
+ IN PROGRESS
117
+
118
+ ## 🔨 Current In Progress Requirement
119
+
120
+ 7: Update PROCESSES.md and the electron app if needed so that when the electron app is watching for REQUIREMENTS file updates, it does not log that a requirement was done until it is done, at which time the REQUIREMENT file "Current Status" changes from "IN PROGRESS" to "DONE".
121
+
122
+ ## Other Section
123
+ Some other content
124
+ `;
125
+
126
+ // Mock the module's internal state
127
+ const fileWatcherModule = require('../../electron-app/src/main/file-watcher');
128
+ fileWatcherModule.lastRequirementsContent = '';
129
+ fileWatcherModule.lastStatus = '';
130
+ fileWatcherModule.progressDots = '';
131
+
132
+ // First call - should set up initial state
133
+ handleRequirementsFileChange(mockFilePath, mockMainWindow);
134
+
135
+ // Second call - DONE status
136
+ mockRequirementsContent = `
137
+ # Requirements
138
+
139
+ ## 🚦 Current Status
140
+
141
+ DONE
142
+
143
+ ## 🔨 Current In Progress Requirement
144
+
145
+ 7: Update PROCESSES.md and the electron app if needed so that when the electron app is watching for REQUIREMENTS file updates, it does not log that a requirement was done until it is done, at which time the REQUIREMENT file "Current Status" changes from "IN PROGRESS" to "DONE".
146
+
147
+ ## Other Section
148
+ Some other content
149
+ `;
150
+
151
+ // Second call - should detect status change and log completion
152
+ handleRequirementsFileChange(mockFilePath, mockMainWindow);
153
+
154
+ // Verify that completion was logged
155
+ expect(consoleSpy.log).toHaveBeenCalledWith('🎉 ===== REQUIREMENT COMPLETED =====');
156
+ expect(consoleSpy.log).toHaveBeenCalledWith('🎯 Status changed from "IN PROGRESS" to "DONE" - logging requirement completion');
157
+ expect(consoleSpy.log).toHaveBeenCalledWith('📋 ===== COMPLETED REQUIREMENT DETAILS =====');
158
+ });
159
+
160
+ test('should show progress dots for IN PROGRESS status', () => {
161
+ const { handleRequirementsFileChange } = require('../../electron-app/src/main/file-watcher');
162
+
163
+ mockRequirementsContent = `
164
+ # Requirements
165
+
166
+ ## 🚦 Current Status
167
+
168
+ IN PROGRESS
169
+
170
+ ## Other Section
171
+ Some other content
172
+ `;
173
+
174
+ // Mock the module's internal state
175
+ const fileWatcherModule = require('../../electron-app/src/main/file-watcher');
176
+ fileWatcherModule.lastRequirementsContent = '';
177
+ fileWatcherModule.lastStatus = '';
178
+ fileWatcherModule.progressDots = '';
179
+
180
+ handleRequirementsFileChange(mockFilePath, mockMainWindow);
181
+
182
+ expect(consoleSpy.log).toHaveBeenCalledWith('⏳ Progress update: .');
183
+ });
184
+
185
+ test('should show progress dots for other status changes', () => {
186
+ const { handleRequirementsFileChange } = require('../../electron-app/src/main/file-watcher');
187
+
188
+ mockRequirementsContent = `
189
+ # Requirements
190
+
191
+ ## 🚦 Current Status
192
+
193
+ READY FOR NEXT REQUIREMENT
194
+
195
+ ## Other Section
196
+ Some other content
197
+ `;
198
+
199
+ // Mock the module's internal state
200
+ const fileWatcherModule = require('../../electron-app/src/main/file-watcher');
201
+ fileWatcherModule.lastRequirementsContent = '';
202
+ fileWatcherModule.lastStatus = '';
203
+ fileWatcherModule.progressDots = '';
204
+
205
+ handleRequirementsFileChange(mockFilePath, mockMainWindow);
206
+
207
+ expect(consoleSpy.log).toHaveBeenCalledWith('📝 File update: .');
208
+ });
209
+ });
210
+
211
+ describe('Integration with Existing Functionality', () => {
212
+ test('should still send requirements-response event to UI', () => {
213
+ const { handleRequirementsFileChange } = require('../../electron-app/src/main/file-watcher');
214
+
215
+ mockRequirementsContent = `
216
+ # Requirements
217
+
218
+ ## RESPONSE FROM LAST CHAT
219
+
220
+ ### ONE LINE STATUS: Test status
221
+ ### ONE LINE SUMMARY: Test summary
222
+ ### MULTILINE DETAILS:
223
+ Test details
224
+
225
+ ## 🚦 Current Status
226
+
227
+ IN PROGRESS
228
+
229
+ ## Other Section
230
+ Some other content
231
+ `;
232
+
233
+ // Mock the module's internal state
234
+ const fileWatcherModule = require('../../electron-app/src/main/file-watcher');
235
+ fileWatcherModule.lastRequirementsContent = '';
236
+ fileWatcherModule.lastStatus = '';
237
+ fileWatcherModule.progressDots = '';
238
+
239
+ handleRequirementsFileChange(mockFilePath, mockMainWindow);
240
+
241
+ // Verify that the UI event was still sent
242
+ expect(mockMainWindow.webContents.send).toHaveBeenCalledWith('requirements-response', expect.objectContaining({
243
+ content: expect.any(String),
244
+ timestamp: expect.any(String),
245
+ filePath: mockFilePath,
246
+ parsedResponse: expect.any(Object)
247
+ }));
248
+ });
249
+
250
+ test('should still send requirements-file-changed event for auto mode', () => {
251
+ const { handleRequirementsFileChange } = require('../../electron-app/src/main/file-watcher');
252
+
253
+ mockRequirementsContent = `
254
+ # Requirements
255
+
256
+ ## 🚦 Current Status
257
+
258
+ IN PROGRESS
259
+
260
+ ## Other Section
261
+ Some other content
262
+ `;
263
+
264
+ // Mock the module's internal state
265
+ const fileWatcherModule = require('../../electron-app/src/main/file-watcher');
266
+ fileWatcherModule.lastRequirementsContent = '';
267
+ fileWatcherModule.lastStatus = '';
268
+ fileWatcherModule.progressDots = '';
269
+
270
+ handleRequirementsFileChange(mockFilePath, mockMainWindow);
271
+
272
+ // Verify that the auto mode event was still sent
273
+ expect(mockMainWindow.webContents.send).toHaveBeenCalledWith('requirements-file-changed');
274
+ });
275
+ });
276
+
277
+ describe('Error Handling', () => {
278
+ test('should handle errors in status parsing gracefully', () => {
279
+ const { parseCurrentStatus } = require('../../electron-app/src/main/file-watcher');
280
+
281
+ // Test with malformed content
282
+ const malformedContent = 'Invalid content without proper sections';
283
+
284
+ const status = parseCurrentStatus(malformedContent);
285
+ expect(status).toBe('');
286
+ });
287
+
288
+ test('should handle errors in requirement details extraction gracefully', () => {
289
+ const { extractCurrentRequirementDetails } = require('../../electron-app/src/main/file-watcher');
290
+
291
+ // Test with malformed content
292
+ const malformedContent = 'Invalid content without proper sections';
293
+
294
+ const details = extractCurrentRequirementDetails(malformedContent);
295
+ expect(details).toBe('');
296
+ });
297
+ });
298
+
299
+ describe('Progress Dots Management', () => {
300
+ test('should reset progress dots when requirement is completed', () => {
301
+ const { handleRequirementsFileChange } = require('../../electron-app/src/main/file-watcher');
302
+
303
+ // Mock the module's internal state with existing progress dots
304
+ const fileWatcherModule = require('../../electron-app/src/main/file-watcher');
305
+ fileWatcherModule.lastRequirementsContent = 'previous content';
306
+ fileWatcherModule.lastStatus = 'IN PROGRESS';
307
+ fileWatcherModule.progressDots = '...';
308
+
309
+ // Change to DONE status
310
+ mockRequirementsContent = `
311
+ # Requirements
312
+
313
+ ## 🚦 Current Status
314
+
315
+ DONE
316
+
317
+ ## 🔨 Current In Progress Requirement
318
+
319
+ 7: Test requirement
320
+
321
+ ## Other Section
322
+ Some other content
323
+ `;
324
+
325
+ handleRequirementsFileChange(mockFilePath, mockMainWindow);
326
+
327
+ // Verify that progress dots were reset
328
+ expect(consoleSpy.log).toHaveBeenCalledWith('🎉 ===== REQUIREMENT COMPLETED =====');
329
+ // The progress dots should be reset internally (we can't directly test this without exposing the variable)
330
+ });
331
+ });
332
+ });
package/jest.config.js ADDED
@@ -0,0 +1,18 @@
1
+ module.exports = {
2
+ testEnvironment: 'node',
3
+ testMatch: ['**/__tests__/**/*.test.js'],
4
+ collectCoverageFrom: [
5
+ 'src/**/*.js',
6
+ '!src/**/*.test.js',
7
+ '!src/**/__tests__/**'
8
+ ],
9
+ coverageDirectory: 'coverage',
10
+ coverageReporters: ['text', 'lcov', 'html'],
11
+ setupFilesAfterEnv: ['<rootDir>/jest.setup.js'],
12
+ moduleNameMapper: {
13
+ '^@/(.*)$': '<rootDir>/src/$1'
14
+ },
15
+ transform: {
16
+ '^.+\\.js$': 'babel-jest'
17
+ }
18
+ };
package/jest.setup.js ADDED
@@ -0,0 +1,12 @@
1
+ // Jest setup file for core package
2
+ // Global test setup and configuration
3
+
4
+ // Mock console methods to reduce noise in tests
5
+ global.console = {
6
+ ...console,
7
+ log: jest.fn(),
8
+ debug: jest.fn(),
9
+ info: jest.fn(),
10
+ warn: jest.fn(),
11
+ error: jest.fn()
12
+ };
package/package.json ADDED
@@ -0,0 +1,46 @@
1
+ {
2
+ "name": "vibecodingmachine-core",
3
+ "version": "1.0.0",
4
+ "description": "Shared core logic for Vibe Coding Machine IDE integration",
5
+ "main": "src/index.cjs",
6
+ "module": "src/index.js",
7
+ "scripts": {
8
+ "build": "echo 'Core package - no build step needed'",
9
+ "test": "jest",
10
+ "test:watch": "jest --watch",
11
+ "test:coverage": "jest --coverage",
12
+ "dev": "echo 'Core package - development mode'"
13
+ },
14
+ "dependencies": {
15
+ "@aws-sdk/client-bedrock-runtime": "^3.932.0",
16
+ "chrome-remote-interface": "^0.33.0",
17
+ "fs-extra": "^11.1.1",
18
+ "jsonwebtoken": "^9.0.2",
19
+ "jwks-rsa": "^3.2.0",
20
+ "node-pty": "^1.0.0"
21
+ },
22
+ "devDependencies": {
23
+ "@babel/core": "^7.23.0",
24
+ "@babel/preset-env": "^7.23.0",
25
+ "babel-jest": "^29.7.0",
26
+ "jest": "^29.7.0"
27
+ },
28
+ "keywords": [
29
+ "ide-integration",
30
+ "chat",
31
+ "autonomous-mode",
32
+ "cdp",
33
+ "applescript"
34
+ ],
35
+ "author": "Vibe Coding Machine Team",
36
+ "license": "MIT",
37
+ "repository": {
38
+ "type": "git",
39
+ "url": "https://github.com/mediawink/vibecodingmachine.git",
40
+ "directory": "packages/core"
41
+ },
42
+ "homepage": "http://vibecodingmachine-website.s3-website-us-east-1.amazonaws.com",
43
+ "bugs": {
44
+ "url": "https://github.com/mediawink/vibecodingmachine/issues"
45
+ }
46
+ }
@@ -0,0 +1,119 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <meta charset="UTF-8">
5
+ <title>Access Denied</title>
6
+ <style>
7
+ body {
8
+ font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
9
+ text-align: center;
10
+ padding: 0;
11
+ margin: 0;
12
+ background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
13
+ min-height: 100vh;
14
+ display: flex;
15
+ align-items: center;
16
+ justify-content: center;
17
+ }
18
+ .container {
19
+ background: white;
20
+ padding: 50px;
21
+ border-radius: 20px;
22
+ box-shadow: 0 20px 60px rgba(0,0,0,0.3);
23
+ max-width: 500px;
24
+ position: relative;
25
+ overflow: hidden;
26
+ }
27
+ .jail-bars {
28
+ position: absolute;
29
+ top: 0;
30
+ left: 0;
31
+ right: 0;
32
+ height: 100%;
33
+ display: flex;
34
+ justify-content: space-around;
35
+ padding: 0 30px;
36
+ pointer-events: none;
37
+ z-index: 10;
38
+ }
39
+ .bar {
40
+ width: 8px;
41
+ background: linear-gradient(to bottom, #555, #333);
42
+ border-radius: 4px;
43
+ box-shadow: 2px 0 4px rgba(0,0,0,0.3);
44
+ }
45
+ .content {
46
+ position: relative;
47
+ z-index: 5;
48
+ animation: slideContent 8s ease-in-out infinite;
49
+ }
50
+ .emoji {
51
+ font-size: 100px;
52
+ margin: 20px 0;
53
+ animation: shake 0.5s infinite;
54
+ }
55
+ @keyframes shake {
56
+ 0%, 100% { transform: translateX(0); }
57
+ 25% { transform: translateX(-5px); }
58
+ 75% { transform: translateX(5px); }
59
+ }
60
+ @keyframes slideContent {
61
+ 0%, 100% { transform: translateX(0); }
62
+ 25% { transform: translateX(15px); }
63
+ 50% { transform: translateX(0); }
64
+ 75% { transform: translateX(-15px); }
65
+ }
66
+ h1 {
67
+ color: #ef4444;
68
+ margin: 20px 0;
69
+ font-size: 32px;
70
+ }
71
+ p {
72
+ color: #666;
73
+ font-size: 18px;
74
+ margin: 15px 0;
75
+ }
76
+ .beta-text {
77
+ background: #fef3c7;
78
+ border: 2px solid #f59e0b;
79
+ border-radius: 10px;
80
+ padding: 20px;
81
+ margin: 25px 0;
82
+ }
83
+ .beta-text strong {
84
+ color: #d97706;
85
+ font-size: 20px;
86
+ }
87
+ .beta-text p {
88
+ margin: 10px 0;
89
+ }
90
+ .close-text {
91
+ margin-top: 30px;
92
+ color: #999;
93
+ font-size: 14px;
94
+ }
95
+ </style>
96
+ </head>
97
+ <body>
98
+ <div class="container">
99
+ <div class="jail-bars">
100
+ <div class="bar"></div>
101
+ <div class="bar"></div>
102
+ <div class="bar"></div>
103
+ <div class="bar"></div>
104
+ <div class="bar"></div>
105
+ <div class="bar"></div>
106
+ </div>
107
+ <div class="content">
108
+ <div class="emoji">🔒</div>
109
+ <h1>Access Denied!</h1>
110
+ <div class="beta-text">
111
+ <strong>Beta Access Only</strong>
112
+ <p style="margin-top: 15px;">Vibe Coding Machine is currently in private beta.</p>
113
+ <p>Want early access? Contact us to join the beta program!</p>
114
+ </div>
115
+ <p class="close-text">You can close this window now.</p>
116
+ </div>
117
+ </div>
118
+ </body>
119
+ </html>