import { matchesGlob } from 'node:path';
const COMMON_METADATA_FIELDS = [
    'repository',
    'homepage',
    'bugs',
    'license',
    'files',
    'publishConfig.access',
];
const COMMON_FORBIDDEN_PATH_PATTERNS = [
    'src/**',
    '**/*.test.*',
    'tsconfig.tsbuildinfo',
];
const PACKED_DEPENDENCY_FIELDS = [
    'dependencies',
    'devDependencies',
    'optionalDependencies',
    'peerDependencies',
];
const PUBLIC_PACKAGE_CONTRACTS = [
    {
        workspaceDir: 'packages/cli',
        publicName: '@open-agent-toolkit/cli',
        role: 'cli',
        requiredMetadataFields: [...COMMON_METADATA_FIELDS, 'bin.oat'],
        requiredPaths: [
            'dist/index.js',
            'assets',
            'assets/migration/pjm-restructure.md',
            'assets/templates/decision.md',
            'assets/templates/repo-agents.md',
            'assets/templates/pjm-agents.md',
            'assets/templates/reference-agents.md',
            'README.md',
        ],
        forbiddenPathPatterns: [...COMMON_FORBIDDEN_PATH_PATTERNS],
        versionPolicyAdditionalRoots: [
            '.agents/skills',
            '.agents/agents',
            '.oat/templates',
            '.oat/scripts',
            'apps/oat-docs/docs',
        ],
        versionPolicyIgnorePatterns: ['assets/**'],
    },
    {
        workspaceDir: 'packages/control-plane',
        publicName: '@open-agent-toolkit/control-plane',
        role: 'support-library',
        requiredMetadataFields: [...COMMON_METADATA_FIELDS, 'exports', 'types'],
        requiredPaths: ['dist/index.js', 'dist/index.d.ts', 'README.md'],
        forbiddenPathPatterns: [...COMMON_FORBIDDEN_PATH_PATTERNS],
        versionPolicyAdditionalRoots: [],
        versionPolicyIgnorePatterns: [],
    },
    {
        workspaceDir: 'packages/docs-config',
        publicName: '@open-agent-toolkit/docs-config',
        role: 'docs-library',
        requiredMetadataFields: [...COMMON_METADATA_FIELDS, 'exports', 'types'],
        requiredPaths: ['dist/index.js', 'dist/index.d.ts', 'README.md'],
        forbiddenPathPatterns: [...COMMON_FORBIDDEN_PATH_PATTERNS],
        versionPolicyAdditionalRoots: [],
        versionPolicyIgnorePatterns: [],
    },
    {
        workspaceDir: 'packages/docs-theme',
        publicName: '@open-agent-toolkit/docs-theme',
        role: 'docs-library',
        requiredMetadataFields: [...COMMON_METADATA_FIELDS, 'exports', 'types'],
        requiredPaths: ['dist/index.js', 'dist/index.d.ts', 'README.md'],
        forbiddenPathPatterns: [...COMMON_FORBIDDEN_PATH_PATTERNS],
        versionPolicyAdditionalRoots: [],
        versionPolicyIgnorePatterns: [],
    },
    {
        workspaceDir: 'packages/docs-transforms',
        publicName: '@open-agent-toolkit/docs-transforms',
        role: 'docs-library',
        requiredMetadataFields: [...COMMON_METADATA_FIELDS, 'exports', 'types'],
        requiredPaths: ['dist/index.js', 'dist/index.d.ts', 'README.md'],
        forbiddenPathPatterns: [...COMMON_FORBIDDEN_PATH_PATTERNS],
        versionPolicyAdditionalRoots: [],
        versionPolicyIgnorePatterns: [],
    },
];
function getMetadataValue(packageJson, fieldPath) {
    return fieldPath.split('.').reduce((value, segment) => {
        if (!value || typeof value !== 'object') {
            return undefined;
        }
        return value[segment];
    }, packageJson);
}
function hasRequiredPackPath(packedPaths, requiredPath) {
    return packedPaths.some((packedPath) => packedPath === requiredPath || packedPath.startsWith(`${requiredPath}/`));
}
export function getPublicPackageContracts() {
    return PUBLIC_PACKAGE_CONTRACTS.map((contract) => ({
        ...contract,
        requiredMetadataFields: [...contract.requiredMetadataFields],
        requiredPaths: [...contract.requiredPaths],
        forbiddenPathPatterns: [...contract.forbiddenPathPatterns],
        versionPolicyAdditionalRoots: [...contract.versionPolicyAdditionalRoots],
        versionPolicyIgnorePatterns: [...contract.versionPolicyIgnorePatterns],
    }));
}
export function findMissingMetadataFields(packageJson, contract) {
    return contract.requiredMetadataFields.filter((fieldPath) => getMetadataValue(packageJson, fieldPath) === undefined);
}
export function findMissingPackedPaths(packedPaths, contract) {
    return contract.requiredPaths.filter((requiredPath) => !hasRequiredPackPath(packedPaths, requiredPath));
}
export function findForbiddenPackedPaths(packedPaths, contract) {
    return packedPaths.filter((packedPath) => contract.forbiddenPathPatterns.some((pattern) => matchesGlob(packedPath, pattern)));
}
export function findWorkspaceProtocolDependencySpecs(packageJson) {
    const workspaceSpecs = [];
    for (const dependencyField of PACKED_DEPENDENCY_FIELDS) {
        const dependencies = packageJson[dependencyField];
        if (!dependencies || typeof dependencies !== 'object') {
            continue;
        }
        for (const [dependencyName, spec] of Object.entries(dependencies)) {
            if (typeof spec === 'string' && spec.startsWith('workspace:')) {
                workspaceSpecs.push(`${dependencyField}.${dependencyName}=${spec}`);
            }
        }
    }
    return workspaceSpecs;
}
export function findNonPublicWorkspaceDependencySpecs(packageJson, publicPackageNames, workspacePackageNames) {
    const publicPackageNameSet = new Set(publicPackageNames);
    const workspacePackageNameSet = new Set(workspacePackageNames);
    const invalidSpecs = [];
    for (const dependencyField of PACKED_DEPENDENCY_FIELDS) {
        const dependencies = packageJson[dependencyField];
        if (!dependencies || typeof dependencies !== 'object') {
            continue;
        }
        for (const [dependencyName, spec] of Object.entries(dependencies)) {
            if (workspacePackageNameSet.has(dependencyName) &&
                !publicPackageNameSet.has(dependencyName)) {
                invalidSpecs.push(`${dependencyField}.${dependencyName}=${String(spec)}`);
            }
        }
    }
    return invalidSpecs;
}
