Skip to content

Commit 9cd412e

Browse files
committed
feat: Added CLAUDE.md and README.md. Commit the package-lock.json file.
1 parent 3912a6a commit 9cd412e

File tree

4 files changed

+6929
-1
lines changed

4 files changed

+6929
-1
lines changed

.gitignore

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@
55
/.nyc_output
66
/dist
77
/lib
8-
/package-lock.json
98
/tmp
109
/yarn.lock
1110
node_modules

CLAUDE.md

Lines changed: 126 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,126 @@
1+
# CLAUDE.md
2+
3+
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
4+
5+
## Project Overview
6+
7+
This is `@codifycli/plugin-test`, a testing framework for Codify plugins. It provides utilities to test plugin lifecycle operations (initialize, validate, plan, apply, import, destroy) by spawning plugin processes and communicating via IPC messages.
8+
9+
## Build and Test Commands
10+
11+
```bash
12+
# Run tests
13+
npm test
14+
15+
# Build the project
16+
npm run prepublishOnly
17+
18+
# Start the project (for testing)
19+
npm start
20+
```
21+
22+
### Running Single Tests
23+
24+
Tests use Vitest. To run a specific test file:
25+
```bash
26+
npx vitest src/test-utils.test.ts
27+
```
28+
29+
To run tests matching a pattern:
30+
```bash
31+
npx vitest --grep "pattern"
32+
```
33+
34+
## Architecture
35+
36+
### Core Components
37+
38+
**PluginTester** (`src/plugin-tester.ts`)
39+
- Main API for testing plugins end-to-end
40+
- `fullTest()`: Executes complete plugin lifecycle (validate → plan → apply → import → modify → destroy)
41+
- `install()`: Tests only installation flow (validate → plan → apply)
42+
- `uninstall()`: Tests destroy operations
43+
- Automatically filters configs by OS using `ResourceConfig.os` field
44+
- Handles multiple configs by adding unique names when needed
45+
46+
**PluginProcess** (`src/plugin-process.ts`)
47+
- Manages individual plugin process lifecycle
48+
- Spawns plugin using `fork()` with tsx loader (`--import tsx/esm`)
49+
- Handles bidirectional IPC communication
50+
- Responds to plugin requests: `COMMAND_REQUEST`, `PRESS_KEY_TO_CONTINUE_REQUEST`, `CODIFY_CREDENTIALS_REQUEST`
51+
- Methods mirror plugin API: `initialize()`, `validate()`, `plan()`, `apply()`, `import()`
52+
- Debug mode: Set `DEBUG` env var to enable `--inspect-brk=9221`
53+
54+
**Spawn Utilities** (`src/spawn.ts`)
55+
- `testSpawn()`: Execute commands interactively in PTY (for testing)
56+
- `spawnSafe()`: Low-level command execution with security checks
57+
- Blocks direct `sudo` usage (must use `requiresRoot` option)
58+
- Strips ANSI codes from output
59+
- Supports stdin passthrough, custom env vars, cwd
60+
61+
**TestUtils** (`src/test-utils.ts`)
62+
- `sendMessageAndAwaitResponse()`: Helper for IPC request/response pattern
63+
- Shell utilities: Detects bash/zsh, provides shell rc paths and source commands
64+
- Platform helpers: `isMacOS()`, `isLinux()`
65+
- Prerequisite installers: `ensureHomebrewInstalledOnMacOs()`, `ensureXcodeInstalledOnMacOs()`
66+
67+
### IPC Communication Flow
68+
69+
1. Test creates `PluginProcess` which forks plugin with IPC enabled
70+
2. Test sends IPC messages (e.g., `{cmd: 'plan', data: {...}, requestId: '...'}`
71+
3. Plugin processes request and may send request messages back (e.g., `COMMAND_REQUEST`)
72+
4. `PluginProcess` intercepts requests, executes via `spawnSafe()`, sends response
73+
5. Plugin completes and sends final response matching original `requestId`
74+
75+
### Plugin Testing Pattern
76+
77+
Typical test structure:
78+
```typescript
79+
// Filter configs by OS automatically
80+
const configs: ResourceConfig[] = [
81+
{ type: 'my-resource', param: 'value', os: [ResourceOs.MACOS] }
82+
];
83+
84+
await PluginTester.fullTest('/path/to/plugin', configs, {
85+
validatePlan: (plans) => {
86+
// Custom assertions on plan results
87+
},
88+
validateApply: (plans) => {
89+
// Custom assertions after apply
90+
},
91+
testModify: {
92+
modifiedConfigs: [/* updated configs */],
93+
validateModify: (plans) => {
94+
// Verify modify operation
95+
}
96+
}
97+
});
98+
```
99+
100+
### OS Filtering
101+
102+
Tests automatically filter configs by OS:
103+
- Configs with `os: [ResourceOs.MACOS]` only run on macOS
104+
- Configs with `os: [ResourceOs.LINUX]` only run on Linux
105+
- No `os` field means runs on all platforms
106+
- Implemented in `PluginTester.fullTest()` using `getPlatformOs()`
107+
108+
## Key Technical Details
109+
110+
- **Module System**: ESM with NodeNext module resolution
111+
- **TypeScript**: Strict mode with decorators support
112+
- **Output**: Compiled to `dist/` directory
113+
- **Node Version**: Requires Node 18+ (configured via `codify.json` for NVM)
114+
- **IPC Validation**: All messages validated against schemas from `@codifycli/schemas` using AJV
115+
- **Security**: Plugins spawned without direct sudo access; must request via `COMMAND_REQUEST`
116+
- **PTY Support**: Uses `@homebridge/node-pty-prebuilt-multiarch` for interactive command execution
117+
- **Shell History**: Commands run with `HISTORY_IGNORE` (bash) or `HISTIGNORE` (zsh) set
118+
119+
## Dependencies
120+
121+
Runtime dependencies (`@codifycli/schemas`, validation libraries, PTY) vs dev dependencies (`@codifycli/plugin-core` for development).
122+
123+
## Environment Variables
124+
125+
- `DEBUG`: Enable plugin debug mode with breakpoint
126+
- `VITE_CODIFY_TEST_JWT`: Required for tests that need Codify credentials

0 commit comments

Comments
 (0)