jettypod 4.4.21 → 4.4.23

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,69 @@
1
+ const { Given, When, Then } = require('@cucumber/cucumber');
2
+ const assert = require('assert');
3
+ const fs = require('fs');
4
+ const path = require('path');
5
+ const { execSync } = require('child_process');
6
+ const { resetDb } = require('../../lib/database');
7
+
8
+ const testDir = path.join('/tmp', 'jettypod-test-' + Date.now());
9
+ let originalDir;
10
+
11
+ Given('I have initialized jettypod', function () {
12
+ resetDb(); // Clear singleton db to avoid stale connections
13
+
14
+ originalDir = process.cwd();
15
+ // SAFETY: Only delete if testDir is in /tmp
16
+ if (fs.existsSync(testDir) && testDir.startsWith('/tmp/')) {
17
+ fs.rmSync(testDir, { recursive: true, force: true });
18
+ }
19
+ fs.mkdirSync(testDir, { recursive: true });
20
+ process.chdir(testDir);
21
+
22
+ execSync('git init', { stdio: 'pipe' });
23
+ execSync('git config user.email "test@test.com"', { stdio: 'pipe' });
24
+ execSync('git config user.name "Test"', { stdio: 'pipe' });
25
+ execSync(`node ${path.join(originalDir, 'jettypod.js')} init`, { stdio: 'pipe', env: { ...process.env, NODE_ENV: 'test' } });
26
+ });
27
+
28
+ Given('I create an epic with id {int}', function (id) {
29
+ execSync(`node ${path.join(originalDir, 'jettypod.js')} work create epic "Test Epic"`, { stdio: 'pipe', env: { ...process.env, NODE_ENV: 'test' } });
30
+ });
31
+
32
+ Given('I create a feature with id {int} under epic {int}', function (featureId, epicId) {
33
+ execSync(`node ${path.join(originalDir, 'jettypod.js')} work create feature "Test Feature" "" --parent=${epicId}`, { stdio: 'pipe', env: { ...process.env, NODE_ENV: 'test' } });
34
+ });
35
+
36
+ When('I start work on item {int}', function (id) {
37
+ execSync(`node ${path.join(originalDir, 'jettypod.js')} work start ${id}`, { stdio: 'pipe', env: { ...process.env, NODE_ENV: 'test' } });
38
+ });
39
+
40
+ Then('the current work file exists', function () {
41
+ const currentWorkPath = path.join(testDir, '.jettypod', 'current-work.json');
42
+ assert(fs.existsSync(currentWorkPath), 'Current work file does not exist');
43
+ });
44
+
45
+ Then('the current work contains item {int}', function (id) {
46
+ const currentWorkPath = path.join(testDir, '.jettypod', 'current-work.json');
47
+ const currentWork = JSON.parse(fs.readFileSync(currentWorkPath, 'utf-8'));
48
+ assert.strictEqual(currentWork.id, id);
49
+ });
50
+
51
+ Then('item {int} status is in_progress or backlog', function (id) {
52
+ // Use CLI to check status to avoid database connection issues
53
+ try {
54
+ const output = execSync(`node ${path.join(originalDir, 'jettypod.js')} work show ${id}`, { encoding: 'utf-8', env: { ...process.env, NODE_ENV: 'test' } });
55
+ const statusMatch = output.match(/Status:\s+(\w+)/);
56
+ if (!statusMatch) {
57
+ throw new Error('Could not find status in output');
58
+ }
59
+ const status = statusMatch[1];
60
+ assert(status === 'in_progress' || status === 'backlog', `Status is ${status}`);
61
+ } finally {
62
+ // SAFETY: Only delete if testDir is in /tmp
63
+ if (fs.existsSync(testDir) && testDir.startsWith('/tmp/')) {
64
+ process.chdir(originalDir);
65
+ fs.rmSync(testDir, { recursive: true, force: true });
66
+ }
67
+ resetDb(); // Clear singleton after cleanup
68
+ }
69
+ });
@@ -0,0 +1,57 @@
1
+ Feature: Work Commands - Stable Mode
2
+ Edge cases and error handling for work commands
3
+
4
+ Scenario: Start work with invalid ID
5
+ Given jettypod is initialized
6
+ When I try to start work with ID "invalid"
7
+ Then I get an error "Invalid work item ID"
8
+
9
+ Scenario: Start work with negative ID
10
+ Given jettypod is initialized
11
+ When I try to start work with ID "-1"
12
+ Then I get an error "Invalid work item ID"
13
+
14
+ Scenario: Start work when not initialized
15
+ Given jettypod is not initialized
16
+ When I try to start work with ID "1"
17
+ Then I get an error "JettyPod not initialized"
18
+
19
+ Scenario: Start work on non-existent item
20
+ Given jettypod is initialized
21
+ When I try to start work with ID "999"
22
+ Then I get an error "Work item #999 not found"
23
+
24
+ Scenario: Stop work with invalid status
25
+ Given I have current work
26
+ When I try to stop work with status "invalid"
27
+ Then I get an error "Invalid status"
28
+
29
+ Scenario: Stop work when no current work
30
+ Given jettypod is initialized
31
+ And no work is active
32
+ When I try to stop work
33
+ Then operation succeeds with no changes
34
+
35
+ Scenario: Get current work with corrupted file
36
+ Given jettypod is initialized
37
+ And current work file is corrupted
38
+ When I get current work
39
+ Then it returns null
40
+
41
+ Scenario: Start work without git repo
42
+ Given jettypod is initialized without git
43
+ And I have a work item
44
+ When I start work on the item
45
+ Then it succeeds without creating branch
46
+
47
+ Scenario: Multiple start work calls
48
+ Given I have a work item
49
+ And I start work on it
50
+ When I start work on a different item
51
+ Then the first item stops being current
52
+ And the second item becomes current
53
+
54
+ Scenario: Start work preserves existing status
55
+ Given I have a work item with status "in_progress"
56
+ When I start work on it
57
+ Then the status remains "in_progress"