761f7cf242
- README: fix LICENSE link, remove dead doc links, update install instructions, remove hardcoded version/bundle size/LOC metrics - artifacthub-pkg.yml: fix appVersion 0.2.18 → 0.2.20, fix README path, fix build-from-source cd path - docs/README.md: trim to only reference files that actually exist (was 160 lines of aspirational links, now 47 lines of real ones) - CLAUDE.md: correct "no MUI imports" claim — code uses @mui/material - headlamp-plugin-developer agent: match corrected MUI convention Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
3.9 KiB
3.9 KiB
CLAUDE.md
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
Project
Headlamp plugin for managing Bitnami Sealed Secrets — client-side encryption, list/detail/create/decrypt SealedSecrets, and sealing key management.
- Plugin name:
sealed-secrets - Runtime dependency:
node-forgefor RSA-OAEP + AES-256-GCM client-side encryption - Target: Headlamp >= v0.13.0
- Reference plugin:
../headlamp-polaris-plugin
Commands
npm start # dev server with hot reload
npm run build # production build
npm run package # package for headlamp
npm run tsc # TypeScript type check (no emit)
npm run lint # ESLint
npm run lint:fix # ESLint with auto-fix
npm run format # Prettier write
npm run format:check # Prettier check
npm test # vitest run
npm run test:watch # vitest watch mode
All tests and tsc must pass before committing.
Architecture
src/
├── index.tsx # Plugin entry: registerRoute, registerSidebarEntry, registerDetailsViewSection, registerPluginSettings
├── types.ts # Branded types, Result type, SealedSecret/SealingKey interfaces
├── headlamp-plugin.d.ts # Module declarations for headlamp plugin
├── hooks/
│ ├── useControllerHealth.ts # Controller pod health monitoring
│ ├── usePermissions.ts # RBAC permission checking
│ └── useSealedSecretEncryption.ts # Encryption workflow hook
├── lib/
│ ├── SealedSecretCRD.ts # CRD definitions and API helpers
│ ├── controller.ts # Sealed Secrets controller interaction
│ ├── crypto.ts # RSA-OAEP + AES-256-GCM encryption via node-forge
│ ├── rbac.ts # RBAC utility functions
│ ├── retry.ts # Retry logic for API calls
│ └── validators.ts # Input validation functions
└── components/
├── SealedSecretList.tsx # List view with create/detail actions
├── SealedSecretDetail.tsx # Detail view for individual SealedSecrets
├── SealingKeysView.tsx # Sealing key management
├── SecretDetailsSection.tsx # Injected into native Secret detail view
├── EncryptDialog.tsx # Client-side encryption dialog
├── DecryptDialog.tsx # Decryption dialog
├── ControllerStatus.tsx # Controller health indicator
├── ErrorBoundary.tsx # ApiErrorBoundary + GenericErrorBoundary
├── LoadingSkeletons.tsx # Loading state skeletons
├── SettingsPage.tsx # Plugin settings
└── VersionWarning.tsx # Controller version compatibility warning
Data flow
Uses custom hooks (hooks/) and a utility library (lib/) instead of a single data context. ErrorBoundary has two variants: ApiErrorBoundary (for route-level) and GenericErrorBoundary (for injected sections). All encryption happens in the browser via node-forge — plaintext secrets never leave the client.
Code conventions
- Functional React components only — no class components
- All imports from
@kinvolk/headlamp-plugin/liband@kinvolk/headlamp-plugin/lib/CommonComponents - MUI (
@mui/material) is available via Headlamp's bundled dependencies — no other UI libraries (no Ant Design, etc.) - TypeScript strict mode — no
any, useunknown+ type guards at API boundaries - Tests: vitest + @testing-library/react, mock with
vi.mock('@kinvolk/headlamp-plugin/lib', ...) vitest.setup.tsprovides a spec-compliantlocalStorageshim for Node 22+ compatibility
Testing
Mock pattern for headlamp APIs:
vi.mock('@kinvolk/headlamp-plugin/lib', () => ({
ApiProxy: { request: vi.fn().mockResolvedValue({}) },
K8s: { ResourceClasses: {} },
}));