import { ParameterError } from '../errors';
import { CONTENT_AS_CODE_VERSION } from './base';
const asCodeObject = (value, resourceLabel, source) => {
    if (typeof value !== 'object' || value === null || Array.isArray(value)) {
        throw new ParameterError(`Invalid ${resourceLabel} file "${source}": expected a YAML object`);
    }
    return value;
};
const requireVersionOne = (value, resourceLabel, source) => {
    if (value.version !== CONTENT_AS_CODE_VERSION) {
        throw new ParameterError(`Invalid ${resourceLabel} file "${source}": expected version ${CONTENT_AS_CODE_VERSION}`);
    }
};
const requireString = (value, key, resourceLabel, source) => {
    const property = value[key];
    if (typeof property !== 'string' || property.trim().length === 0) {
        throw new ParameterError(`Invalid ${resourceLabel} file "${source}": expected a non-empty ${key}`);
    }
    return property;
};
const requireStringArray = (value, key, resourceLabel, source) => {
    const property = value[key];
    if (!Array.isArray(property) ||
        property.some((item) => typeof item !== 'string')) {
        throw new ParameterError(`Invalid ${resourceLabel} file "${source}": expected ${key} to be an array of strings`);
    }
    return property;
};
export const parseVersionedContentAsCodeDocument = ({ input, source, resourceLabel, contentType, version = CONTENT_AS_CODE_VERSION, identityKey = 'slug', }) => {
    const value = asCodeObject(input, resourceLabel, source);
    if (value.contentType !== contentType) {
        throw new ParameterError(`Invalid contentType in ${resourceLabel} file "${source}": expected "${contentType}"`);
    }
    if (value.version !== version) {
        throw new ParameterError(`Invalid ${resourceLabel} file "${source}": expected version ${version}`);
    }
    requireString(value, identityKey, resourceLabel, source);
    return value;
};
export const parseCustomRoleAsCode = (input, source) => {
    const value = asCodeObject(input, 'custom role', source);
    requireVersionOne(value, 'custom role', source);
    const name = requireString(value, 'name', 'custom role', source);
    if (value.description !== null && typeof value.description !== 'string') {
        throw new ParameterError(`Invalid custom role file "${source}": expected description to be a string or null`);
    }
    if (value.level !== 'project' && value.level !== 'organization') {
        throw new ParameterError(`Invalid custom role file "${source}": expected level to be project or organization`);
    }
    return {
        version: CONTENT_AS_CODE_VERSION,
        name,
        description: value.description,
        level: value.level,
        scopes: requireStringArray(value, 'scopes', 'custom role', source),
    };
};
export const parseGroupAsCode = (input, source) => {
    const value = asCodeObject(input, 'group', source);
    requireVersionOne(value, 'group', source);
    return {
        version: CONTENT_AS_CODE_VERSION,
        name: requireString(value, 'name', 'group', source),
        members: requireStringArray(value, 'members', 'group', source),
    };
};
const parseUserRole = (value, source) => {
    const role = asCodeObject(value, 'user role', source);
    if (role.type !== 'system' && role.type !== 'custom') {
        throw new ParameterError(`Invalid user file "${source}": expected role type to be system or custom`);
    }
    return {
        type: role.type,
        name: requireString(role, 'name', 'user', source),
    };
};
export const parseUserAsCode = (input, source) => {
    const value = asCodeObject(input, 'user', source);
    requireVersionOne(value, 'user', source);
    if (typeof value.disabled !== 'boolean') {
        throw new ParameterError(`Invalid user file "${source}": expected disabled to be a boolean`);
    }
    return {
        version: CONTENT_AS_CODE_VERSION,
        email: requireString(value, 'email', 'user', source),
        disabled: value.disabled,
        role: parseUserRole(value.role, source),
    };
};
//# sourceMappingURL=parsers.js.map