fix: simplify package content check and facets label
This commit is contained in:
parent
9e6e7e3550
commit
8930688a95
@ -6,7 +6,7 @@
|
||||
* - path field defaults, allowed/disallowed values
|
||||
* - takt.min_version format validation
|
||||
* - Version comparison (numeric, not lexicographic)
|
||||
* - Empty package detection (faceted/ and pieces/ presence)
|
||||
* - Empty package detection (facets/ and pieces/ presence)
|
||||
*/
|
||||
|
||||
import { describe, it, expect, beforeEach, afterEach } from 'vitest';
|
||||
@ -241,7 +241,7 @@ describe('checkPackageHasContent', () => {
|
||||
rmSync(tempDir, { recursive: true, force: true });
|
||||
});
|
||||
|
||||
it('should throw when neither faceted/ nor pieces/ exists', () => {
|
||||
it('should throw when neither facets/ nor pieces/ exists', () => {
|
||||
// Given: empty package root directory
|
||||
// When: content check is performed
|
||||
// Then: throws an error (empty package not allowed)
|
||||
@ -256,9 +256,9 @@ describe('checkPackageHasContent', () => {
|
||||
})).toThrow(/path: \.takt/);
|
||||
});
|
||||
|
||||
it('should not throw when only faceted/ exists', () => {
|
||||
// Given: package with faceted/ only
|
||||
mkdirSync(join(tempDir, 'faceted'), { recursive: true });
|
||||
it('should not throw when only facets/ exists', () => {
|
||||
// Given: package with facets/ only
|
||||
mkdirSync(join(tempDir, 'facets'), { recursive: true });
|
||||
|
||||
// When: content check is performed
|
||||
// Then: no error (facet-only package is valid)
|
||||
@ -274,15 +274,16 @@ describe('checkPackageHasContent', () => {
|
||||
expect(() => checkPackageHasContent(tempDir)).not.toThrow();
|
||||
});
|
||||
|
||||
it('should not throw when both faceted/ and pieces/ exist', () => {
|
||||
it('should not throw when both facets/ and pieces/ exist', () => {
|
||||
// Given: package with both directories
|
||||
mkdirSync(join(tempDir, 'faceted'), { recursive: true });
|
||||
mkdirSync(join(tempDir, 'facets'), { recursive: true });
|
||||
mkdirSync(join(tempDir, 'pieces'), { recursive: true });
|
||||
|
||||
// When: content check is performed
|
||||
// Then: no error
|
||||
expect(() => checkPackageHasContent(tempDir)).not.toThrow();
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
@ -118,7 +118,7 @@ export async function ensembleAddCommand(spec: string): Promise<void> {
|
||||
});
|
||||
|
||||
const targets = collectCopyTargets(packageRoot);
|
||||
const facetFiles = targets.filter(t => t.relativePath.startsWith('faceted/'));
|
||||
const facetFiles = targets.filter(t => t.relativePath.startsWith('facets/'));
|
||||
const pieceFiles = targets.filter(t => t.relativePath.startsWith('pieces/'));
|
||||
|
||||
const facetSummary = summarizeFacetsByType(facetFiles.map(t => t.relativePath));
|
||||
@ -135,7 +135,7 @@ export async function ensembleAddCommand(spec: string): Promise<void> {
|
||||
const editPieces = detectEditPieces(pieceYamls);
|
||||
|
||||
info(`\n📦 ${owner}/${repo} @${ref}`);
|
||||
info(` faceted: ${facetSummary}`);
|
||||
info(` facets: ${facetSummary}`);
|
||||
if (pieceFiles.length > 0) {
|
||||
const pieceNames = pieceFiles.map(t =>
|
||||
t.relativePath.replace(/^pieces\//, '').replace(/\.yaml$/, ''),
|
||||
|
||||
@ -6,7 +6,7 @@
|
||||
* - path field validation (no absolute paths, no directory traversal)
|
||||
* - min_version format validation (strict semver X.Y.Z)
|
||||
* - Numeric semver comparison
|
||||
* - Package content presence check (faceted/ or pieces/ must exist)
|
||||
* - Package content presence check (facets/ or pieces/ must exist)
|
||||
* - Realpath validation to prevent symlink-based traversal outside root
|
||||
*/
|
||||
|
||||
@ -105,15 +105,15 @@ export function isVersionCompatible(minVersion: string, currentVersion: string):
|
||||
}
|
||||
|
||||
/**
|
||||
* Check that the package root contains at least one of faceted/ or pieces/.
|
||||
* Check that the package root contains at least one of facets/ or pieces/.
|
||||
* Throws if neither exists (empty package).
|
||||
*/
|
||||
export function checkPackageHasContent(packageRoot: string): void {
|
||||
const hasFaceted = existsSync(join(packageRoot, 'faceted'));
|
||||
const hasFaceted = existsSync(join(packageRoot, 'facets'));
|
||||
const hasPieces = existsSync(join(packageRoot, 'pieces'));
|
||||
if (!hasFaceted && !hasPieces) {
|
||||
throw new Error(
|
||||
`Package at "${packageRoot}" has neither faceted/ nor pieces/ directory — empty package rejected`,
|
||||
`Package at "${packageRoot}" has neither facets/ nor pieces/ directory — empty package rejected`,
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -128,17 +128,17 @@ export function checkPackageHasContentWithContext(
|
||||
packageRoot: string,
|
||||
context: PackageContentCheckContext,
|
||||
): void {
|
||||
const hasFaceted = existsSync(join(packageRoot, 'faceted'));
|
||||
const hasFacets = existsSync(join(packageRoot, 'facets'));
|
||||
const hasPieces = existsSync(join(packageRoot, 'pieces'));
|
||||
if (hasFaceted || hasPieces) return;
|
||||
if (hasFacets || hasPieces) return;
|
||||
|
||||
const checkedFaceted = join(packageRoot, 'faceted');
|
||||
const checkedFaceted = join(packageRoot, 'facets');
|
||||
const checkedPieces = join(packageRoot, 'pieces');
|
||||
const configuredPath = context.configuredPath ?? '.';
|
||||
const manifestPath = context.manifestPath ?? '(unknown)';
|
||||
const hint = configuredPath === '.'
|
||||
? `hint: If your package content is under ".takt/", set "path: .takt" in ${TAKT_PACKAGE_MANIFEST_FILENAME}.`
|
||||
: `hint: Verify "path: ${configuredPath}" points to a directory containing faceted/ or pieces/.`;
|
||||
: `hint: Verify "path: ${configuredPath}" points to a directory containing facets/ or pieces/.`;
|
||||
|
||||
throw new Error(
|
||||
[
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user