import type { Config } from '../config/schema.js';
export type MobilePairUrlValidationCode = 'INVALID_URL' | 'LOOPBACK_NOT_REACHABLE';
export type MobilePairUrlValidationResult = {
    ok: true;
    url: string;
    loopback: false;
} | {
    ok: false;
    code: MobilePairUrlValidationCode;
    message: string;
};
/** Normalize a gateway root URL (no trailing slash, no path). */
export declare function normalizeGatewayBaseUrl(raw: string): string | null;
/** True when a phone on the network cannot reach this gateway root URL. */
export declare function isLoopbackGatewayBaseUrl(raw: string): boolean;
export declare function validateMobilePairBaseUrl(raw: string): MobilePairUrlValidationResult;
export type ParsedMobileConnectDeepLink = {
    baseUrl: string;
    lanUrl: string | null;
    pairingSecret: string;
};
/** Parse `xopc://gateway/mobile-connect?...` payloads from QR codes. */
export declare function parseMobileConnectDeepLink(raw: string): ParsedMobileConnectDeepLink | null;
/**
 * Ordered URLs for mobile clients. Priority:
 *   1. reverse-proxy public URL (user-deployed HTTPS, typically fastest + works on cellular)
 *   2. LAN URL (zero-RTT on same network)
 *   3. baseUrl (legacy: usually the FRP tunnel public URL, kept for callers that
 *      do not yet split reverseProxyUrl from tunnelUrl)
 *   4. tunnelUrl (explicit FRP tunnel URL, kept as a fallback even when a
 *      reverse-proxy URL is also configured)
 *
 * Loopback URLs are dropped (they only work on the gateway host) and
 * duplicates are de-duped while preserving first occurrence order.
 */
export declare function buildMobileConnectUrlOrder(params: {
    baseUrl: string | null | undefined;
    lanUrl: string | null | undefined;
    reverseProxyUrl?: string | null | undefined;
    tunnelUrl?: string | null | undefined;
}): string[];
/** First LAN URL when the gateway listens on a network-accessible bind host. */
export declare function resolveMobilePairLanUrl(config: Config): string | null;
