import DatabaseProperty from "./Database/DatabaseProperty";
import BadDataException from "./Exception/BadDataException";
import { ObjectType } from "./JSON";
import Zod from "../Utils/Schema/Zod";
class Domain extends DatabaseProperty {
    /**
     * Checks if a domain is a test/reserved domain that can skip DNS verification.
     * Test domains include .example.com, .example.org, .example.net, and .test TLDs.
     * These are reserved by IANA for documentation and testing purposes.
     */
    static isTestDomain(domain) {
        const domainLower = domain.toLowerCase().trim();
        return Domain.TEST_DOMAIN_SUFFIXES.some((suffix) => {
            return domainLower.endsWith(suffix);
        });
    }
    get domain() {
        return this._domain;
    }
    set domain(v) {
        const isValid = Domain.isValidDomain(v);
        if (!isValid) {
            throw new BadDataException("Domain " + v + " is not in valid format.");
        }
        this._domain = v;
    }
    static isValidDomain(domain) {
        /*
         * Regex-based domain validation
         * - Each label (part between dots) must be 1-63 characters
         * - Labels can contain alphanumeric characters and hyphens
         * - Labels cannot start or end with a hyphen
         * - TLD must be at least 2 characters and contain only letters
         * - Total length should not exceed 253 characters
         */
        if (!domain || domain.length > 253) {
            return false;
        }
        /*
         * Domain validation regex:
         * ^                                          - start of string
         * (?:[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?\.)+  - one or more labels followed by dot
         * [a-zA-Z]{2,63}                             - TLD: 2-63 letters only
         * $                                          - end of string
         */
        const domainRegex = /^(?:[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?\.)+[a-zA-Z]{2,63}$/;
        return domainRegex.test(domain);
    }
    constructor(domain) {
        super();
        this._domain = "";
        this.domain = domain;
    }
    toString() {
        return this.domain;
    }
    static toDatabase(value) {
        if (value) {
            if (typeof value === "string") {
                value = new Domain(value);
            }
            return value.toString();
        }
        return null;
    }
    toJSON() {
        return {
            _type: ObjectType.Domain,
            value: this.toString(),
        };
    }
    static fromJSON(json) {
        if (json["_type"] === ObjectType.Domain) {
            return new Domain(json["value"] || "");
        }
        throw new BadDataException("Invalid JSON: " + JSON.stringify(json));
    }
    static fromDatabase(_value) {
        if (_value) {
            return new Domain(_value);
        }
        return null;
    }
    static getSchema() {
        return Zod.object({
            _type: Zod.literal(ObjectType.Domain),
            value: Zod.string().openapi({
                type: "string",
                example: "example.com",
            }),
        }).openapi({
            type: "object",
            description: "Domain object",
            example: { _type: ObjectType.Domain, value: "example.com" },
        });
    }
}
/*
 * Reserved TLDs for testing and documentation (per IANA)
 * These domains can never have real DNS records, so they're safe for testing
 */
Domain.TEST_DOMAIN_SUFFIXES = [
    ".example.com",
    ".example.org",
    ".example.net",
    ".test",
];
export default Domain;
//# sourceMappingURL=Domain.js.map