"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.ABTestSchema = exports.TrafficAllocationConfigSchema = exports.TrafficRouteOnHeaderSchema = exports.GatewayFilterSchema = exports.ABTestEvaluationConfigSchema = exports.PerVariantOnlineEvaluationConfigSchema = exports.ABTestVariantSchema = exports.VariantConfigurationSchema = exports.TargetRefSchema = exports.ConfigurationBundleRefSchema = exports.VariantWeightSchema = exports.VariantNameSchema = exports.ABTestModeSchema = exports.ABTestDescriptionSchema = exports.ABTestNameSchema = void 0;
const zod_1 = require("zod");
// ============================================================================
// AB Test Types
// ============================================================================
exports.ABTestNameSchema = zod_1.z
    .string()
    .min(1, 'Name is required')
    .max(48)
    .regex(/^[a-zA-Z][a-zA-Z0-9_]{0,47}$/, 'Must begin with a letter and contain only alphanumeric characters and underscores (max 48 chars)');
exports.ABTestDescriptionSchema = zod_1.z.string().min(1).max(200).optional();
exports.ABTestModeSchema = zod_1.z.enum(['config-bundle', 'target-based']).optional().default('config-bundle');
exports.VariantNameSchema = zod_1.z.enum(['C', 'T1']);
exports.VariantWeightSchema = zod_1.z.number().int().min(1).max(100);
// ── Config Bundle variant configuration ────────────────────────────────────
exports.ConfigurationBundleRefSchema = zod_1.z.object({
    bundleArn: zod_1.z.string().min(1),
    bundleVersion: zod_1.z.string().min(1),
});
// ── Target-based variant configuration ─────────────────────────────────────
exports.TargetRefSchema = zod_1.z.object({
    targetName: zod_1.z.string().min(1).max(100),
});
// ── Variant configuration union ────────────────────────────────────────────
// Exactly one of configurationBundle or target must be set (XOR).
const ConfigBundleVariantConfigSchema = zod_1.z.object({
    configurationBundle: exports.ConfigurationBundleRefSchema,
    target: zod_1.z.never().optional(),
});
const TargetVariantConfigSchema = zod_1.z.object({
    configurationBundle: zod_1.z.never().optional(),
    target: exports.TargetRefSchema,
});
exports.VariantConfigurationSchema = zod_1.z.union([ConfigBundleVariantConfigSchema, TargetVariantConfigSchema]);
exports.ABTestVariantSchema = zod_1.z.object({
    name: exports.VariantNameSchema,
    weight: exports.VariantWeightSchema,
    variantConfiguration: exports.VariantConfigurationSchema,
});
// ── Evaluation config union ────────────────────────────────────────────────
exports.PerVariantOnlineEvaluationConfigSchema = zod_1.z.object({
    treatmentName: exports.VariantNameSchema,
    onlineEvaluationConfigArn: zod_1.z.string().min(1),
});
exports.ABTestEvaluationConfigSchema = zod_1.z.union([
    zod_1.z.object({ onlineEvaluationConfigArn: zod_1.z.string().min(1) }),
    zod_1.z.object({
        perVariantOnlineEvaluationConfig: zod_1.z.array(exports.PerVariantOnlineEvaluationConfigSchema).length(2),
    }),
]);
// ── Gateway filter ─────────────────────────────────────────────────────────
exports.GatewayFilterSchema = zod_1.z.object({
    targetPaths: zod_1.z.array(zod_1.z.string().min(1).max(500)).max(1),
});
// ── Traffic allocation ─────────────────────────────────────────────────────
exports.TrafficRouteOnHeaderSchema = zod_1.z.object({
    headerName: zod_1.z.string().min(1),
});
exports.TrafficAllocationConfigSchema = zod_1.z.object({
    routeOnHeader: exports.TrafficRouteOnHeaderSchema,
});
// ── AB Test schema ─────────────────────────────────────────────────────────
exports.ABTestSchema = zod_1.z
    .object({
    name: exports.ABTestNameSchema,
    description: exports.ABTestDescriptionSchema,
    mode: exports.ABTestModeSchema,
    gatewayRef: zod_1.z.string().min(1),
    roleArn: zod_1.z.string().min(1).optional(),
    variants: zod_1.z.array(exports.ABTestVariantSchema).length(2),
    evaluationConfig: exports.ABTestEvaluationConfigSchema,
    gatewayFilter: exports.GatewayFilterSchema.optional(),
    trafficAllocationConfig: exports.TrafficAllocationConfigSchema.optional(),
    maxDurationDays: zod_1.z.number().int().min(1).max(90).optional(),
    enableOnCreate: zod_1.z.boolean().optional(),
    promoted: zod_1.z.boolean().optional(),
})
    .refine(data => {
    const names = data.variants.map(v => v.name);
    return names.includes('C') && names.includes('T1');
}, { message: 'Variants must include exactly one control (C) and one treatment (T1)', path: ['variants'] })
    .refine(data => data.variants.reduce((sum, v) => sum + v.weight, 0) === 100, {
    message: 'Variant weights must sum to 100',
    path: ['variants'],
})
    .refine(data => {
    if (data.mode === 'target-based') {
        return data.variants.every(v => v.variantConfiguration.target != null);
    }
    return data.variants.every(v => v.variantConfiguration.configurationBundle != null);
}, {
    message: 'Target-based mode requires target on each variant; config-bundle mode requires configurationBundle',
    path: ['variants'],
});
//# sourceMappingURL=ab-test.js.map