{"version":3,"file":"index.cjs","names":["PACKAGE_NAME","VERSION","PACKAGE_NAME","VERSION","validateAccessKey","ACCESS_KEY_PATTERN","validateCompanyId","validateCompanyId","validateAccessKey","ACCESS_KEY_PATTERN","validateAccessKey","ACCESS_KEY_PATTERN","validateCompanyId","validateInvoiceId","validateStateTaxId","buildQueryString","validateCompanyId","validateCompanyId","validateInvoiceId","validateCompanyId","validateCompanyId","validateCompanyId","validateCompanyId","PKG_VERSION","nfeFactory","PKG_NAME","PKG_VERSION"],"sources":["../src/core/errors/index.ts","../src/version.ts","../src/core/http/client.ts","../src/core/utils/polling.ts","../src/core/types.ts","../src/core/resources/service-invoices.ts","../src/core/utils/certificate-validator.ts","../src/core/resources/companies.ts","../src/core/resources/legal-people.ts","../src/core/resources/natural-people.ts","../src/core/resources/webhooks.ts","../src/core/resources/addresses.ts","../src/core/resources/transportation-invoices.ts","../src/core/resources/inbound-product-invoices.ts","../src/core/resources/product-invoice-query.ts","../src/core/utils/unserved-route.ts","../src/core/resources/consumer-invoice-query.ts","../src/core/resources/legal-entity-lookup.ts","../src/core/resources/natural-person-lookup.ts","../src/core/resources/tax-calculation.ts","../src/core/resources/tax-codes.ts","../src/core/resources/product-invoices.ts","../src/core/resources/state-taxes.ts","../src/core/resources/service-invoices-rtc.ts","../src/core/resources/product-invoices-rtc.ts","../src/core/resources/municipal-taxes.ts","../src/core/resources/consumer-invoices.ts","../src/core/resources/certificates.ts","../src/core/resources/notifications.ts","../src/core/resources/index.ts","../src/core/client.ts","../src/index.ts"],"sourcesContent":["/**\n * NFE.io SDK v3 - Error Classes\n *\n * Comprehensive error handling system that maintains compatibility\n * with v2 error types while providing modern TypeScript benefits\n */\n\n// ============================================================================\n// Base Error Class\n// ============================================================================\n\nexport class NfeError extends Error {\n  public readonly type: string = 'NfeError';\n  public readonly code?: number | undefined;\n  public readonly status?: number | undefined;\n  public readonly details?: unknown;\n  public readonly raw?: unknown;\n\n  constructor(message: string, details?: unknown, code?: number) {\n    super(message);\n    this.name = this.constructor.name;\n    this.code = code;\n    this.status = code; // Alias for compatibility\n    this.details = details;\n    this.raw = details;\n\n    // Ensure proper prototype chain for instanceof checks\n    Object.setPrototypeOf(this, new.target.prototype);\n\n    // Capture stack trace if available (Node.js specific)\n    if ('captureStackTrace' in Error && typeof (Error as any).captureStackTrace === 'function') {\n      (Error as any).captureStackTrace(this, this.constructor);\n    }\n  }\n\n  // Alias for statusCode (used in tests)\n  get statusCode(): number | undefined {\n    return this.code;\n  }\n\n  /** Convert error to JSON for logging/debugging */\n  toJSON() {\n    return {\n      type: this.type,\n      name: this.name,\n      message: this.message,\n      code: this.code,\n      details: this.details,\n      stack: this.stack,\n    };\n  }\n}\n\n// ============================================================================\n// HTTP-specific Errors (maintain v2 compatibility)\n// ============================================================================\n\nexport class AuthenticationError extends NfeError {\n  public override readonly type = 'AuthenticationError';\n\n  constructor(message = 'Invalid API key or authentication failed', details?: unknown) {\n    super(message, details, 401);\n  }\n}\n\nexport class ValidationError extends NfeError {\n  public override readonly type = 'ValidationError';\n\n  constructor(message = 'Invalid request data', details?: unknown) {\n    super(message, details, 400);\n  }\n}\n\nexport class NotFoundError extends NfeError {\n  public override readonly type = 'NotFoundError';\n\n  constructor(message = 'Resource not found', details?: unknown) {\n    super(message, details, 404);\n  }\n}\n\nexport class ConflictError extends NfeError {\n  public override readonly type = 'ConflictError';\n\n  constructor(message = 'Resource conflict', details?: unknown) {\n    super(message, details, 409);\n  }\n}\n\nexport class RateLimitError extends NfeError {\n  public override readonly type = 'RateLimitError';\n\n  constructor(message = 'Rate limit exceeded', details?: unknown) {\n    super(message, details, 429);\n  }\n}\n\nexport class ServerError extends NfeError {\n  public override readonly type = 'ServerError';\n\n  constructor(message = 'Internal server error', details?: unknown, code = 500) {\n    super(message, details, code);\n  }\n}\n\n// ============================================================================\n// Connection/Network Errors\n// ============================================================================\n\nexport class ConnectionError extends NfeError {\n  public override readonly type = 'ConnectionError';\n\n  constructor(message = 'Connection error', details?: unknown) {\n    super(message, details);\n  }\n}\n\nexport class TimeoutError extends NfeError {\n  public override readonly type = 'TimeoutError';\n\n  constructor(message = 'Request timeout', details?: unknown) {\n    super(message, details);\n  }\n}\n\n// ============================================================================\n// SDK-specific Errors\n// ============================================================================\n\nexport class ConfigurationError extends NfeError {\n  public override readonly type = 'ConfigurationError';\n\n  constructor(message = 'SDK configuration error', details?: unknown) {\n    super(message, details);\n  }\n}\n\nexport class PollingTimeoutError extends NfeError {\n  public override readonly type = 'PollingTimeoutError';\n\n  constructor(message = 'Polling timeout - operation still in progress', details?: unknown) {\n    super(message, details);\n  }\n}\n\nexport class InvoiceProcessingError extends NfeError {\n  public override readonly type = 'InvoiceProcessingError';\n\n  constructor(message = 'Invoice processing failed', details?: unknown) {\n    super(message, details);\n  }\n}\n\n// ============================================================================\n// Error Factory (maintains v2 compatibility)\n// ============================================================================\n\nexport class ErrorFactory {\n  /**\n   * Create error from HTTP response (maintains v2 ResourceError.generate pattern)\n   */\n  static fromHttpResponse(status: number, data?: unknown, message?: string): NfeError {\n    const errorMessage = message || this.getDefaultMessage(status);\n\n    switch (status) {\n      case 400:\n        return new ValidationError(errorMessage, data);\n      case 401:\n        return new AuthenticationError(errorMessage, data);\n      case 404:\n        return new NotFoundError(errorMessage, data);\n      case 409:\n        return new ConflictError(errorMessage, data);\n      case 429:\n        return new RateLimitError(errorMessage, data);\n      case 500:\n      case 502:\n      case 503:\n      case 504:\n        return new ServerError(errorMessage, data, status);\n      default:\n        if (status >= 400 && status < 500) {\n          return new ValidationError(errorMessage, data);\n        }\n        if (status >= 500) {\n          return new ServerError(errorMessage, data, status);\n        }\n        return new NfeError(errorMessage, data, status);\n    }\n  }\n\n  /**\n   * Create error from fetch/network issues\n   */\n  static fromNetworkError(error: Error): NfeError {\n    if (error.name === 'AbortError' || error.message.includes('timeout')) {\n      return new TimeoutError('Request timeout', error);\n    }\n\n    if (error.message.includes('fetch')) {\n      return new ConnectionError('Network connection failed', error);\n    }\n\n    return new ConnectionError('Connection error', error);\n  }\n\n  /**\n   * Create error from Node.js version check\n   */\n  static fromNodeVersionError(nodeVersion: string): ConfigurationError {\n    return new ConfigurationError(\n      `NFE.io SDK v3 requires Node.js 18+ (for native fetch support). Current version: ${nodeVersion}`,\n      { nodeVersion, requiredVersion: '>=18.0.0' }\n    );\n  }\n\n  /**\n   * Create error from missing API key\n   */\n  static fromMissingApiKey(): ConfigurationError {\n    return new ConfigurationError(\n      'API key is required. Pass it in NfeConfig or set NFE_API_KEY environment variable.',\n      { configField: 'apiKey' }\n    );\n  }\n\n  private static getDefaultMessage(status: number): string {\n    const messages: Record<number, string> = {\n      400: 'Invalid request data',\n      401: 'Invalid API key or authentication failed',\n      403: 'Access forbidden',\n      404: 'Resource not found',\n      409: 'Resource conflict',\n      429: 'Rate limit exceeded',\n      500: 'Internal server error',\n      502: 'Bad gateway',\n      503: 'Service unavailable',\n      504: 'Gateway timeout',\n    };\n\n    return messages[status] || `HTTP ${status} error`;\n  }\n}\n\n// ============================================================================\n// Error Type Guards\n// ============================================================================\n\nexport function isNfeError(error: unknown): error is NfeError {\n  return error instanceof NfeError;\n}\n\nexport function isAuthenticationError(error: unknown): error is AuthenticationError {\n  return error instanceof AuthenticationError;\n}\n\nexport function isValidationError(error: unknown): error is ValidationError {\n  return error instanceof ValidationError;\n}\n\nexport function isNotFoundError(error: unknown): error is NotFoundError {\n  return error instanceof NotFoundError;\n}\n\nexport function isConnectionError(error: unknown): error is ConnectionError {\n  return error instanceof ConnectionError;\n}\n\nexport function isTimeoutError(error: unknown): error is TimeoutError {\n  return error instanceof TimeoutError;\n}\n\nexport function isPollingTimeoutError(error: unknown): error is PollingTimeoutError {\n  return error instanceof PollingTimeoutError;\n}\n\n// ============================================================================\n// Legacy Aliases (for v2 compatibility)\n// ============================================================================\n\n/** @deprecated Use ValidationError instead */\nexport const BadRequestError = ValidationError;\n\n/** @deprecated Use NfeError instead */\nexport const APIError = NfeError;\n\n/** @deprecated Use ServerError instead */\nexport const InternalServerError = ServerError;\n\n// Export all error types\nexport const ErrorTypes = {\n  NfeError,\n  AuthenticationError,\n  ValidationError,\n  NotFoundError,\n  ConflictError,\n  RateLimitError,\n  ServerError,\n  ConnectionError,\n  TimeoutError,\n  ConfigurationError,\n  PollingTimeoutError,\n  InvoiceProcessingError,\n  // Legacy aliases\n  BadRequestError,\n  APIError,\n  InternalServerError,\n} as const;\n\nexport type ErrorType = keyof typeof ErrorTypes;\n","/**\n * Identidade do pacote — GERADO por `scripts/generate-version.ts`.\n *\n * NÃO editar à mão, e NÃO fixar literal em outro lugar: até 2026-09-02 havia três\n * versões diferentes no repositório e o User-Agent reportava uma quarta, inexistente.\n * `tests/unit/version.test.ts` compara estas constantes com o `package.json` e\n * falha na divergência.\n */\n\n/** Nome do pacote como publicado no npm. */\nexport const PACKAGE_NAME = 'nfe-io';\n\n/** Versão desta build, vinda do `package.json`. */\nexport const VERSION = '6.0.0';\n","/**\n * NFE.io SDK v3 - HTTP Client with Fetch API\n *\n * Modern HTTP client using native fetch (Node.js 18+)\n * Zero external dependencies with automatic retries and proper error handling\n */\n\nimport type { HttpConfig, HttpResponse, RetryConfig } from '../types.js';\nimport {\n  ErrorFactory,\n  ConnectionError,\n  TimeoutError,\n  RateLimitError,\n  NfeError\n} from '../errors/index.js';\nimport { PACKAGE_NAME, VERSION } from '../../version.js';\n\n// Simple type declarations for runtime APIs\ndeclare const fetch: any;\ndeclare const AbortController: any;\ndeclare const URLSearchParams: any;\ndeclare const FormData: any;\ndeclare const setTimeout: any;\ndeclare const clearTimeout: any;\ndeclare const Buffer: any;\ndeclare const process: any;\n\n// ============================================================================\n// HTTP Client Implementation\n// ============================================================================\n\nexport class HttpClient {\n  private readonly config: HttpConfig;\n\n  constructor(config: HttpConfig) {\n    this.config = config;\n    this.validateFetchSupport();\n  }\n\n  // --------------------------------------------------------------------------\n  // Public HTTP Methods\n  // --------------------------------------------------------------------------\n\n  async get<T = unknown>(\n    path: string,\n    params?: Record<string, unknown>,\n    customHeaders?: Record<string, string>\n  ): Promise<HttpResponse<T>> {\n    const url = this.buildUrl(path, params);\n    return this.request<T>('GET', url, undefined, customHeaders);\n  }\n\n  async post<T = unknown>(path: string, data?: unknown): Promise<HttpResponse<T>> {\n    const url = this.buildUrl(path);\n    return this.request<T>('POST', url, data);\n  }\n\n  async put<T = unknown>(path: string, data?: unknown): Promise<HttpResponse<T>> {\n    const url = this.buildUrl(path);\n    return this.request<T>('PUT', url, data);\n  }\n\n  async delete<T = unknown>(path: string): Promise<HttpResponse<T>> {\n    const url = this.buildUrl(path);\n    return this.request<T>('DELETE', url);\n  }\n\n  async patch<T = unknown>(path: string, data?: unknown): Promise<HttpResponse<T>> {\n    const url = this.buildUrl(path);\n    return this.request<T>('PATCH', url, data);\n  }\n\n  /**\n   * HEAD request — returns status/headers, no body. Non-2xx still throws via the\n   * error factory (e.g. 404 → NotFoundError), so callers checking existence\n   * should catch NotFoundError and treat it as \"not found\".\n   */\n  async head(path: string): Promise<HttpResponse<void>> {\n    const url = this.buildUrl(path);\n    return this.request<void>('HEAD', url);\n  }\n\n  /**\n   * GET request expecting a binary buffer response (e.g., PDF, XML downloads).\n   *\n   * Sends an Accept header for the given content type and returns the response body as a Buffer.\n   */\n  async getBuffer(path: string, accept: string = 'application/octet-stream'): Promise<HttpResponse<Buffer>> {\n    const url = this.buildUrl(path);\n    return this.request<Buffer>('GET', url, undefined, { 'Accept': accept });\n  }\n\n  // --------------------------------------------------------------------------\n  // Core Request Method with Retry Logic\n  // --------------------------------------------------------------------------\n\n  private async request<T>(\n    method: string,\n    url: string,\n    data?: unknown,\n    customHeaders?: Record<string, string>\n  ): Promise<HttpResponse<T>> {\n    const { maxRetries, baseDelay } = this.config.retryConfig;\n    let lastError: NfeError | undefined;\n\n    for (let attempt = 0; attempt <= maxRetries; attempt++) {\n      try {\n        const response = await this.executeRequest<T>(method, url, data, customHeaders);\n        return response;\n      } catch (error) {\n        lastError = error as NfeError;\n\n        // Don't retry on client errors (4xx) except rate limits\n        if (this.shouldNotRetry(lastError, attempt, maxRetries)) {\n          throw lastError;\n        }\n\n        // Wait before retry (exponential backoff)\n        if (attempt < maxRetries) {\n          const delay = this.calculateRetryDelay(attempt, baseDelay);\n          await this.sleep(delay);\n        }\n      }\n    }\n\n    throw lastError || new ConnectionError('Request failed after all retries');\n  }\n\n  // --------------------------------------------------------------------------\n  // Single Request Execution\n  // --------------------------------------------------------------------------\n\n  private async executeRequest<T>(\n    method: string,\n    url: string,\n    data?: unknown,\n    customHeaders?: Record<string, string>\n  ): Promise<HttpResponse<T>> {\n    const controller = new AbortController();\n    const timeoutId = setTimeout(() => controller.abort(), this.config.timeout);\n\n    try {\n      const headers = this.buildHeaders(data, customHeaders);\n      const body = this.buildBody(data);\n\n      const response = await fetch(url, {\n        method: method.toUpperCase(),\n        headers,\n        body,\n        signal: controller.signal,\n      });\n\n      clearTimeout(timeoutId);\n\n      return await this.processResponse<T>(response);\n\n    } catch (error) {\n      clearTimeout(timeoutId);\n\n      // Re-throw NfeError instances (from handleErrorResponse)\n      if (error instanceof NfeError) {\n        throw error;\n      }\n\n      if (error instanceof Error) {\n        if (error.name === 'AbortError') {\n          throw new TimeoutError(`Request timeout after ${this.config.timeout}ms`, error);\n        }\n        throw ErrorFactory.fromNetworkError(error);\n      }\n\n      throw new ConnectionError('Unknown network error', error);\n    }\n  }\n\n  // --------------------------------------------------------------------------\n  // Response Processing\n  // --------------------------------------------------------------------------\n\n  private async processResponse<T>(response: any): Promise<HttpResponse<T>> {\n    // Special handling for NFE.io async responses (202 with location)\n    if (response.status === 202) {\n      const location = response.headers.get('location');\n      if (location) {\n        return {\n          data: {\n            code: 202,\n            status: 'pending',\n            location\n          } as T,\n          status: response.status,\n          headers: this.extractHeaders(response)\n        };\n      }\n    }\n\n    // Handle 204 No Content\n    if (response.status === 204) {\n      return {\n        data: {} as T,\n        status: response.status,\n        headers: this.extractHeaders(response)\n      };\n    }\n\n    // Handle error responses\n    if (!response.ok) {\n      await this.handleErrorResponse(response);\n    }\n\n    // Parse successful response\n    const data = await this.parseResponseData<T>(response);\n\n    return {\n      data,\n      status: response.status,\n      headers: this.extractHeaders(response)\n    };\n  }\n\n  private async parseResponseData<T>(response: any): Promise<T> {\n    const contentType = response.headers.get('content-type') || '';\n\n    if (contentType.includes('application/json')) {\n      return response.json() as Promise<T>;\n    }\n\n    if (contentType.includes('application/pdf') || contentType.includes('application/xml')) {\n      const buffer = await response.arrayBuffer();\n      return Buffer.from(buffer) as unknown as T;\n    }\n\n    // Default to text\n    return response.text() as unknown as T;\n  }\n\n  private async handleErrorResponse(response: any): Promise<never> {\n    let errorData: unknown;\n\n    try {\n      const contentType = response.headers.get('content-type') || '';\n      if (contentType.includes('application/json')) {\n        errorData = await response.json();\n      } else {\n        errorData = await response.text();\n      }\n    } catch {\n      // Ignore parse errors, use status as fallback\n      errorData = { status: response.status, statusText: response.statusText };\n    }\n\n    // Extract error message from response data\n    const message = this.extractErrorMessage(errorData, response.status);\n\n    throw ErrorFactory.fromHttpResponse(response.status, errorData, message);\n  }\n\n  /**\n   * Extrai a mensagem de erro do corpo devolvido pela API.\n   *\n   * A plataforma usa QUATRO envelopes distintos, todos medidos ao vivo em\n   * 2026-09-02 (e o de ModelState capturado em `tests/fixtures/live-contracts/`):\n   *\n   *   \"pageCount must be between 1 and 50\"                    string JSON crua\n   *   {\"code\":40001,\"message\":\"environment has to be ...\"}    campo `message`\n   *   {\"errors\":[{\"message\":\"access key is not valid\"}]}      lista (hosts de consulta)\n   *   {\"title\":\"...\",\"errors\":{\"file\":[\"The File field ...\"]}} ProblemDetails/ModelState\n   *\n   * Só os dois primeiros eram tratados. Nos outros dois a mensagem real era\n   * descartada e o chamador recebia `HTTP 400 error` — literalmente o status que\n   * ele já tinha. Foi assim que o campo errado no upload de certificado\n   * (`The File field is required.`) ficou invisível por meses.\n   */\n  private extractErrorMessage(data: unknown, status: number): string {\n    if (typeof data === 'object' && data !== null) {\n      const errorObj = data as Record<string, unknown>;\n\n      // Try common error message fields\n      if (typeof errorObj.message === 'string') return errorObj.message;\n      if (typeof errorObj.error === 'string') return errorObj.error;\n      if (typeof errorObj.detail === 'string') return errorObj.detail;\n      if (typeof errorObj.details === 'string') return errorObj.details;\n\n      const fromErrors = this.extractFromErrorsField(errorObj.errors);\n      if (fromErrors) return fromErrors;\n\n      // ProblemDetails sem detalhe por campo: `title` é o que sobra.\n      if (typeof errorObj.title === 'string') return errorObj.title;\n    }\n\n    if (typeof data === 'string') {\n      return data;\n    }\n\n    return `HTTP ${status} error`;\n  }\n\n  /**\n   * Lê o campo `errors`, que vem em duas formas conforme o serviço:\n   * lista de `{message}` (hosts de consulta) ou mapa `campo -> string[]`\n   * (ModelState do ASP.NET).\n   */\n  private extractFromErrorsField(errors: unknown): string | undefined {\n    if (!errors || typeof errors !== 'object') return undefined;\n\n    if (Array.isArray(errors)) {\n      const messages = errors\n        .map(item => {\n          if (typeof item === 'string') return item;\n          if (item && typeof item === 'object') {\n            const message = (item as Record<string, unknown>).message;\n            if (typeof message === 'string') return message;\n          }\n          return undefined;\n        })\n        .filter((m): m is string => Boolean(m));\n\n      return messages.length > 0 ? messages.join('; ') : undefined;\n    }\n\n    // ModelState: { campo: [\"mensagem\", ...] }\n    const parts: string[] = [];\n    for (const [field, value] of Object.entries(errors as Record<string, unknown>)) {\n      const messages = Array.isArray(value)\n        ? value.filter((v): v is string => typeof v === 'string')\n        : typeof value === 'string'\n          ? [value]\n          : [];\n      if (messages.length > 0) parts.push(`${field}: ${messages.join(', ')}`);\n    }\n\n    return parts.length > 0 ? parts.join('; ') : undefined;\n  }\n\n  // --------------------------------------------------------------------------\n  // URL and Header Building\n  // --------------------------------------------------------------------------\n\n  private buildUrl(path: string, params?: Record<string, unknown>): string {\n    const baseUrl = this.config.baseUrl.replace(/\\/$/, ''); // Remove trailing slash\n    const cleanPath = path.replace(/^\\//, ''); // Remove leading slash\n    let url = `${baseUrl}/${cleanPath}`;\n\n    if (params && Object.keys(params).length > 0) {\n      const searchParams = new URLSearchParams();\n      for (const [key, value] of Object.entries(params)) {\n        if (value !== undefined && value !== null) {\n          searchParams.append(key, String(value));\n        }\n      }\n      const queryString = searchParams.toString();\n      if (queryString) {\n        url += `?${queryString}`;\n      }\n    }\n\n    return url;\n  }\n\n  private buildHeaders(data?: unknown, customHeaders?: Record<string, string>): Record<string, string> {\n    const headers: Record<string, string> = {\n      'X-NFE-APIKEY': this.config.apiKey,\n      'Accept': 'application/json',\n      'User-Agent': this.getUserAgent(),\n    };\n\n    // Add Content-Type for requests with body (but not FormData)\n    if (data !== undefined && data !== null && !this.isFormData(data)) {\n      headers['Content-Type'] = 'application/json';\n    }\n\n    // Merge custom headers (allowing override of defaults)\n    if (customHeaders) {\n      Object.assign(headers, customHeaders);\n    }\n\n    return headers;\n  }\n\n  private buildBody(data?: unknown): string | any | undefined {\n    if (data === undefined || data === null) {\n      return undefined;\n    }\n\n    // Handle FormData (for file uploads)\n    if (this.isFormData(data)) {\n      return data as any;\n    }\n\n    // Default to JSON\n    return JSON.stringify(data);\n  }\n\n  private isFormData(data: unknown): boolean {\n    return typeof FormData !== 'undefined' && data instanceof FormData;\n  }\n\n  /**\n   * Identificação do SDK no fio.\n   *\n   * Nome e versão vêm de `src/version.ts`, gerado do `package.json` — NÃO fixar\n   * literal aqui. Até 2026-09-02 esta função devolvia `@nfe-io/sdk@3.0.0`: nome de\n   * pacote que não existe (o publicado é `nfe-io`) e versão três majors atrás.\n   * Nos 30 dias anteriores, 93.995 requisições chegaram ao gateway com esse valor,\n   * em 23 variantes de User-Agent e 5 majors de Node — e nenhuma informação sobre\n   * a versão do SDK. Era o único sinal de adoção que a plataforma tinha.\n   */\n  private getUserAgent(): string {\n    const nodeVersion = process.version;\n    const platform = process.platform;\n\n    return `${PACKAGE_NAME}@${VERSION} node/${nodeVersion} (${platform})`;\n  }\n\n  private extractHeaders(response: any): Record<string, string> {\n    const headers: Record<string, string> = {};\n    response.headers.forEach((value: any, key: any) => {\n      headers[key] = value;\n    });\n    return headers;\n  }\n\n  // --------------------------------------------------------------------------\n  // Retry Logic\n  // --------------------------------------------------------------------------\n\n  private shouldNotRetry(error: NfeError, attempt: number, maxRetries: number): boolean {\n    // Don't retry if we've exhausted attempts\n    if (attempt >= maxRetries) {\n      return true;\n    }\n\n    // Always retry rate limits (with backoff)\n    if (error instanceof RateLimitError) {\n      return false;\n    }\n\n    // Don't retry client errors (4xx) - these are permanent errors\n    if (error.code && error.code >= 400 && error.code < 500) {\n      return true; // Don't retry any 4xx errors\n    }\n\n    // Retry server errors (5xx) and network errors\n    return false;\n  }\n\n  private calculateRetryDelay(attempt: number, baseDelay: number): number {\n    const { maxDelay = 30000, backoffMultiplier = 2 } = this.config.retryConfig;\n\n    // Exponential backoff with jitter\n    const exponentialDelay = baseDelay * Math.pow(backoffMultiplier, attempt);\n    const jitter = Math.random() * 0.1 * exponentialDelay; // 10% jitter\n\n    return Math.min(exponentialDelay + jitter, maxDelay);\n  }\n\n  private sleep(ms: number): Promise<void> {\n    return new Promise(resolve => setTimeout(resolve, ms));\n  }\n\n  // --------------------------------------------------------------------------\n  // Validation\n  // --------------------------------------------------------------------------\n\n  private validateFetchSupport(): void {\n    if (typeof fetch === 'undefined') {\n      throw ErrorFactory.fromNodeVersionError(process.version);\n    }\n\n    if (typeof AbortController === 'undefined') {\n      throw new ConnectionError(\n        'AbortController is not available. This should not happen in Node.js 18+.'\n      );\n    }\n  }\n}\n\n// ============================================================================\n// HTTP Client Factory\n// ============================================================================\n\nexport function createHttpClient(config: HttpConfig): HttpClient {\n  return new HttpClient(config);\n}\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Create default retry configuration\n */\nexport function createDefaultRetryConfig(): Required<RetryConfig> {\n  return {\n    maxRetries: 3,\n    baseDelay: 1000,\n    maxDelay: 30000,\n    backoffMultiplier: 2,\n  };\n}\n\n/**\n * Build HTTP config from SDK config\n */\nexport function buildHttpConfig(apiKey: string, baseUrl: string, timeout: number, retryConfig: RetryConfig): HttpConfig {\n  return {\n    apiKey,\n    baseUrl,\n    timeout,\n    retryConfig,\n  };\n}\n","/**\n * NFE.io SDK v3 - Polling Utility\n *\n * Generic polling utility for handling asynchronous operations\n * with exponential backoff, timeout enforcement, and progress tracking.\n */\n\nimport { TimeoutError } from '../errors/index.js';\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport interface PollingOptions<T> {\n  /**\n   * Function to execute on each poll attempt\n   */\n  fn: () => Promise<T>;\n\n  /**\n   * Function to determine if polling should stop\n   * Returns true when the desired state is reached\n   */\n  isComplete: (result: T) => boolean;\n\n  /**\n   * Total timeout in milliseconds\n   * @default 120000 (2 minutes)\n   */\n  timeout?: number;\n\n  /**\n   * Initial delay before first poll in milliseconds\n   * @default 1000 (1 second)\n   */\n  initialDelay?: number;\n\n  /**\n   * Maximum delay between polls in milliseconds\n   * @default 10000 (10 seconds)\n   */\n  maxDelay?: number;\n\n  /**\n   * Backoff multiplier for exponential backoff\n   * @default 1.5\n   */\n  backoffFactor?: number;\n\n  /**\n   * Callback invoked after each poll attempt\n   * Useful for progress tracking and logging\n   */\n  onPoll?: (attempt: number, result: T) => void;\n\n  /**\n   * Optional error handler for non-fatal errors\n   * Return true to continue polling, false to abort\n   */\n  onError?: (error: Error, attempt: number) => boolean;\n}\n\n// ============================================================================\n// Polling Utility\n// ============================================================================\n\n/**\n * Generic polling utility with exponential backoff\n *\n * @template T - Type of the result being polled\n * @param options - Polling configuration options\n * @returns Promise that resolves with the final result\n * @throws {TimeoutError} If polling exceeds timeout\n * @throws {Error} If fn() throws and onError doesn't handle it\n *\n * @example\n * ```typescript\n * const invoice = await poll({\n *   fn: () => nfe.serviceInvoices.retrieve('company-id', 'invoice-id'),\n *   isComplete: (inv) => ['Issued', 'IssueFailed'].includes(inv.flowStatus),\n *   timeout: 120000,\n *   onPoll: (attempt, inv) => console.log(`Attempt ${attempt}: ${inv.flowStatus}`)\n * });\n * ```\n */\nexport async function poll<T>(options: PollingOptions<T>): Promise<T> {\n  const {\n    fn,\n    isComplete,\n    timeout = 120000, // 2 minutes default\n    initialDelay = 1000, // 1 second default\n    maxDelay = 10000, // 10 seconds default\n    backoffFactor = 1.5,\n    onPoll,\n    onError,\n  } = options;\n\n  const startTime = Date.now();\n  let delay = initialDelay;\n  let attempt = 0;\n\n  // eslint-disable-next-line no-constant-condition\n  while (true) {\n    attempt++;\n\n    try {\n      // Execute polling function\n      const result = await fn();\n\n      // Invoke progress callback if provided\n      if (onPoll) {\n        onPoll(attempt, result);\n      }\n\n      // Check if we're done\n      if (isComplete(result)) {\n        return result;\n      }\n\n      // Check if we'll exceed timeout after next delay\n      const elapsed = Date.now() - startTime;\n      if (elapsed + delay > timeout) {\n        throw new TimeoutError(\n          `Polling timeout exceeded after ${attempt} attempts (${elapsed}ms)`,\n          408\n        );\n      }\n\n      // Wait before next poll\n      await sleep(delay);\n\n      // Calculate next delay with exponential backoff\n      delay = Math.min(delay * backoffFactor, maxDelay);\n    } catch (error) {\n      // If it's a timeout error we threw, re-throw it\n      if (error instanceof TimeoutError) {\n        throw error;\n      }\n\n      // Allow custom error handling\n      if (onError && error instanceof Error) {\n        const shouldContinue = onError(error, attempt);\n        if (shouldContinue) {\n          // Check timeout before continuing\n          const elapsed = Date.now() - startTime;\n          if (elapsed + delay > timeout) {\n            throw new TimeoutError(\n              `Polling timeout exceeded after ${attempt} attempts with errors (${elapsed}ms)`,\n              408\n            );\n          }\n          await sleep(delay);\n          delay = Math.min(delay * backoffFactor, maxDelay);\n          continue;\n        }\n      }\n\n      // Re-throw unhandled errors\n      throw error;\n    }\n  }\n}\n\n/**\n * Sleep utility\n *\n * @param ms - Milliseconds to sleep\n * @returns Promise that resolves after the specified time\n */\nfunction sleep(ms: number): Promise<void> {\n  return new Promise((resolve) => setTimeout(resolve, ms));\n}\n\n// ============================================================================\n// Helper Functions\n// ============================================================================\n\n/**\n * Create a polling configuration for common scenarios\n *\n * @param timeout - Total timeout in milliseconds\n * @returns Pre-configured polling options\n *\n * @example\n * ```typescript\n * const result = await poll({\n *   ...createPollingConfig(60000), // 1 minute\n *   fn: () => checkStatus(),\n *   isComplete: (status) => status === 'complete'\n * });\n * ```\n */\nexport function createPollingConfig(timeout: number): Pick<PollingOptions<unknown>, 'timeout' | 'initialDelay' | 'maxDelay' | 'backoffFactor'> {\n  return {\n    timeout,\n    initialDelay: 1000,\n    maxDelay: Math.min(10000, timeout / 10), // 10% of timeout or 10s\n    backoffFactor: 1.5,\n  };\n}\n\n/**\n * Poll with a simple retry count instead of time-based timeout\n *\n * @template T - Type of the result\n * @param fn - Function to execute\n * @param isComplete - Completion check\n * @param maxAttempts - Maximum number of attempts\n * @param delayMs - Delay between attempts in milliseconds\n * @returns Promise with the result\n *\n * @example\n * ```typescript\n * const result = await pollWithRetries(\n *   () => fetchData(),\n *   (data) => data.ready,\n *   10, // max 10 attempts\n *   2000 // 2 seconds between attempts\n * );\n * ```\n */\nexport async function pollWithRetries<T>(\n  fn: () => Promise<T>,\n  isComplete: (result: T) => boolean,\n  maxAttempts: number,\n  delayMs: number\n): Promise<T> {\n  let attempt = 0;\n\n  while (attempt < maxAttempts) {\n    attempt++;\n    const result = await fn();\n\n    if (isComplete(result)) {\n      return result;\n    }\n\n    if (attempt < maxAttempts) {\n      await sleep(delayMs);\n    }\n  }\n\n  throw new Error(`Polling failed after ${maxAttempts} attempts`);\n}\n","/**\n * NFE.io SDK v3 - Core Types\n *\n * TypeScript definitions for NFE.io API v1\n *\n * This file re-exports generated types and adds SDK-specific types\n * for configuration, HTTP client, and high-level operations.\n */\n\n// ============================================================================\n// SDK-Specific Types (not in generated code)\n// ============================================================================\n\n// Configuration Types\n// ----------------------------------------------------------------------------\n\nexport interface NfeConfig {\n  /**\n   * API key for every FISCAL host — `api.nfe.io` and `api.nfse.io`.\n   *\n   * Covers companies, service/product/consumer invoices (incl. RTC), certificates,\n   * municipal and state taxes, tax calculation, tax codes, webhooks, and the\n   * inbound CT-e / NF-e distribution resources.\n   */\n  apiKey?: string;\n  /**\n   * API key for the LOOKUP hosts — `nfe.api.nfe.io`, `legalentity.api.nfe.io`,\n   * `naturalperson.api.nfe.io`, `address.api.nfe.io`.\n   *\n   * Covers address (CEP), legal entity (CNPJ), natural person (CPF) and the\n   * product/consumer invoice *query* resources.\n   *\n   * **The two keys are NOT interchangeable.** Each is rejected with HTTP 403 on\n   * the other family's hosts — verified live on 2026-09-01, see\n   * `tests/fixtures/live-contracts/api-key-host-matrix.json`. Setting this key\n   * does not affect any fiscal resource.\n   *\n   * Optional: falls back to {@link NfeConfig.apiKey} when omitted. Note the\n   * fallback is one-way — a client configured with ONLY `dataApiKey` cannot\n   * reach fiscal resources and throws `ConfigurationError` when one is accessed.\n   */\n  dataApiKey?: string;\n  /** Environment to use (both use same endpoint, differentiated by API key) */\n  environment?: 'production' | 'development';\n  /** Custom base URL (overrides environment) */\n  baseUrl?: string;\n  /** Request timeout in milliseconds */\n  timeout?: number;\n  /** Retry configuration */\n  retryConfig?: RetryConfig;\n}\n\nexport interface RetryConfig {\n  /** Maximum number of retry attempts */\n  maxRetries: number;\n  /** Base delay between retries in milliseconds */\n  baseDelay: number;\n  /** Maximum delay between retries in milliseconds */\n  maxDelay?: number;\n  /** Backoff multiplier */\n  backoffMultiplier?: number;\n}\n\n// HTTP Types\n// ----------------------------------------------------------------------------\n\nexport interface HttpConfig {\n  baseUrl: string;\n  apiKey: string;\n  timeout: number;\n  retryConfig: RetryConfig;\n}\n\nexport interface HttpResponse<T = unknown> {\n  data: T;\n  status: number;\n  headers: Record<string, string>;\n}\n\nexport interface AsyncResponse {\n  code: 202;\n  status: 'pending';\n  location: string;\n}\n\n// Service Invoice Specific Types\n// ----------------------------------------------------------------------------\n\n/** Flow status for service invoice processing */\nexport type FlowStatus =\n  | 'CancelFailed'\n  | 'IssueFailed'\n  | 'Issued'\n  | 'Cancelled'\n  | 'PullFromCityHall'\n  | 'WaitingCalculateTaxes'\n  | 'WaitingDefineRpsNumber'\n  | 'WaitingSend'\n  | 'WaitingSendCancel'\n  | 'WaitingReturn'\n  | 'WaitingDownload';\n\n/** Terminal states that end async processing */\nexport const TERMINAL_FLOW_STATES: FlowStatus[] = [\n  'Issued',\n  'IssueFailed',\n  'Cancelled',\n  'CancelFailed',\n];\n\n/** Check if a flow status is terminal (ends processing) */\nexport function isTerminalFlowStatus(status: FlowStatus): boolean {\n  return TERMINAL_FLOW_STATES.includes(status);\n}\n\n/** Async response with extracted invoice ID */\nexport interface ServiceInvoiceAsyncResponse extends AsyncResponse {\n  /** Invoice ID extracted from location header */\n  invoiceId: string;\n}\n\n/** Options for listing service invoices */\nexport interface ListServiceInvoicesOptions extends PaginationOptions {\n  /** Filter by issued date start (yyyy-MM-dd) */\n  issuedBegin?: string;\n  /** Filter by issued date end (yyyy-MM-dd) */\n  issuedEnd?: string;\n  /** Filter by created date start (yyyy-MM-dd) */\n  createdBegin?: string;\n  /** Filter by created date end (yyyy-MM-dd) */\n  createdEnd?: string;\n  /** Include totals in response */\n  hasTotals?: boolean;\n}\n\n/** Options for automatic polling in createAndWait */\nexport interface PollingOptions {\n  /** Total timeout in milliseconds @default 120000 (2 minutes) */\n  timeout?: number;\n  /** Initial delay before first poll @default 1000 (1 second) */\n  initialDelay?: number;\n  /** Maximum delay between polls @default 10000 (10 seconds) */\n  maxDelay?: number;\n  /** Backoff multiplier for exponential backoff @default 1.5 */\n  backoffFactor?: number;\n  /** Callback invoked after each poll attempt */\n  onPoll?: (attempt: number, flowStatus: FlowStatus) => void;\n}\n\n/** Response from sendEmail operation */\nexport interface SendEmailResponse {\n  /** Whether email was sent successfully */\n  sent: boolean;\n  /** Optional message about the send operation */\n  message?: string;\n}\n\n// Backward Compatibility Type Aliases\n// ----------------------------------------------------------------------------\n\n/** Additional invoice details (withholdings, deductions) */\nexport type ServiceInvoiceDetails = {\n  issWithheld?: number;\n  pisWithheld?: number;\n  cofinsWithheld?: number;\n  csllWithheld?: number;\n  irrfWithheld?: number;\n  inssWithheld?: number;\n  deductions?: number;\n  additionalInformation?: string;\n};\n\n// Entity Type Aliases (from generated enums)\n// ----------------------------------------------------------------------------\n\nexport type EntityType = 'Undefined' | 'NaturalPerson' | 'LegalEntity';\nexport type TaxRegime = 'Isento' | 'MicroempreendedorIndividual' | 'SimplesNacional' | 'LucroPresumido' | 'LucroReal';\nexport type SpecialTaxRegime = 'Automatico' | 'Nenhum' | 'MicroempresaMunicipal' | 'Estimativa' | 'SociedadeDeProfissionais' | 'Cooperativa' | 'MicroempreendedorIndividual' | 'MicroempresarioEmpresaPequenoPorte';\n\n\n\n\n\n\n\n// ============================================================================\n// Webhook Types\n// ============================================================================\n\n/**\n * @deprecated Este shape (`url`/`events`/`active`) não corresponde ao contrato real da\n * API de webhooks (confirmado ao vivo em 2026-07-02: a API rejeita `url` com\n * `400 \"The Uri field is required\"`). Use {@link AccountWebhook} com os métodos\n * account-scoped (`listAccountWebhooks`, `createAccountWebhook`, ...).\n */\nexport interface Webhook {\n  /** Webhook ID */\n  id?: string;\n  /** Target URL */\n  url: string;\n  /** Webhook events */\n  events: WebhookEvent[];\n  /** Is active */\n  active?: boolean;\n  /** Secret for signature validation */\n  secret?: string;\n  /** Creation timestamp */\n  createdOn?: string;\n  /** Last update timestamp */\n  modifiedOn?: string;\n}\n\n/**\n * @deprecated Estes literais (`invoice.*`) não existem na API real — os event types\n * vivos seguem o padrão `service_invoice.issued_successfully` etc. Use\n * {@link WebhookEventType} (lista viva via `webhooks.fetchEventTypes()`).\n */\nexport type WebhookEvent = 'invoice.created' | 'invoice.issued' | 'invoice.cancelled' | 'invoice.failed';\n\n/**\n * Webhook de conta — shape real do recurso em `/v2/webhooks`, conforme os specs\n * oficiais (`openapi/spec/nf-servico-v1.yaml` e equivalentes) e confirmado ao vivo\n * (2026-07-02).\n *\n * Nota de contrato: o spec declara `contentType`/`status` como enums inteiros, mas a\n * API serializa strings (`\"json\"`, `\"Active\"`) — o tipo segue o formato de fio real.\n */\nexport interface AccountWebhook {\n  /** ID exclusivo do webhook (GUID gerado pela API) */\n  id?: string;\n  /** URL de entrega das notificações. Verificada com ping na criação (exige 2xx). */\n  uri: string;\n  /** Media type das entregas (a API serializa string, ex.: `\"json\"`) */\n  contentType?: 'json' | (string & {});\n  /**\n   * Segredo de 32–64 caracteres usado no HMAC-SHA1 do header `X-Hub-Signature`.\n   * Ecoado na resposta do create; omitido em list/retrieve (write-only na leitura).\n   */\n  secret?: string;\n  /** Filtros de event types (ver {@link WebhookEventType} e `fetchEventTypes()`) */\n  filters?: Array<WebhookEventType | (string & {})>;\n  /** Pular verificação do certificado SSL do host da URI (padrão: `false`) */\n  insecureSsl?: boolean;\n  /** Cabeçalhos HTTP adicionais enviados nas entregas */\n  headers?: Record<string, string>;\n  /** Propriedades adicionais incluídas no corpo das notificações */\n  properties?: Record<string, unknown>;\n  /** Status do webhook (a API serializa string, ex.: `\"Active\"`) */\n  status?: 'Active' | (string & {});\n  /** Data de criação */\n  createdOn?: string;\n  /** Data de modificação */\n  modifiedOn?: string;\n}\n\n/**\n * Event types reais de webhook, extraídos de `GET /v2/webhooks/eventTypes` ao vivo\n * (2026-07-02). União aberta: ids novos do servidor continuam aceitos sem quebra.\n * Prefira `webhooks.fetchEventTypes()` para a lista viva.\n *\n * (O id `legal_entity_taxpayer:updated_sucessfully` — com `:` e grafia `sucessfully` —\n * é reproduzido exatamente como a API o retorna.)\n */\nexport type WebhookEventType =\n  | 'service_invoice.issued'\n  | 'service_invoice.issued_successfully'\n  | 'service_invoice.issued_error'\n  | 'service_invoice.issued_failed'\n  | 'service_invoice.cancelled'\n  | 'service_invoice.cancelled_successfully'\n  | 'service_invoice.cancelled_error'\n  | 'service_invoice.cancelled_failed'\n  | 'service_invoice.pulled'\n  | 'service_invoice_inbound.issued_successfully'\n  | 'service_invoice_inbound.event_raised_successfully'\n  | 'product_invoice.issued_successfully'\n  | 'product_invoice.issued_error'\n  | 'product_invoice.issued_failed'\n  | 'product_invoice.cancelled_successfully'\n  | 'product_invoice.cancelled_error'\n  | 'product_invoice.cancelled_failed'\n  | 'product_invoice.cce_successfully'\n  | 'product_invoice.cce_error'\n  | 'product_invoice.cce_failed'\n  | 'product_invoice.dfe_event_successfully'\n  | 'product_invoice.dfe_event_error'\n  | 'product_invoice.dfe_event_failed'\n  | 'product_invoice.disabled_successfully'\n  | 'product_invoice.disabled_error'\n  | 'product_invoice.disabled_failed'\n  | 'product_invoice_inbound.issued_successfully'\n  | 'product_invoice_inbound.event_raised_successfully'\n  | 'product_invoice_inbound.input_event_raised_successfully'\n  | 'product_invoice_inbound_summary.issued_successfully'\n  | 'product_invoice_inbound_summary.event_raised_successfully'\n  | 'consumer_invoice.issued_successfully'\n  | 'consumer_invoice.issued_error'\n  | 'consumer_invoice.issued_failed'\n  | 'consumer_invoice.cancelled_successfully'\n  | 'consumer_invoice.cancelled_error'\n  | 'consumer_invoice.cancelled_failed'\n  | 'transportation_invoice_inbound.issued_successfully'\n  | 'transportation_invoice_inbound.event_raised_successfully'\n  | 'legal_entity_taxpayer:updated_sucessfully'\n  | 'product_tax.created_successfully'\n  | 'product_tax.creation_failed'\n  | 'product_tax.custom_rules_requested'\n  | 'tax_payment_form.created_successfully'\n  | 'tax_payment_form.creation_failed'\n  | 'tax_payment_form.creation_not_needed'\n  | (string & {});\n\n// ============================================================================\n// Address Types (for Address Lookup API)\n// ============================================================================\n\n/**\n * City information with IBGE code\n */\nexport interface AddressCity {\n  /** IBGE city code */\n  code: string;\n  /** City name */\n  name: string;\n}\n\n/**\n * Complete address information from Correios DNE\n */\nexport interface Address {\n  /** State abbreviation (e.g., 'SP', 'RJ') */\n  state: string;\n  /** City information with IBGE code */\n  city: AddressCity;\n  /** District/neighborhood name */\n  district: string;\n  /** Additional address information */\n  additionalInformation: string;\n  /** Street type suffix (e.g., 'Avenida', 'Rua') */\n  streetSuffix: string;\n  /** Street name */\n  street: string;\n  /** Address number (may be a textual range, e.g. \"de 612 a 1510 - lado par\") */\n  number: string;\n  /** Minimum number in range (omitted by the API for some entries) */\n  numberMin?: string;\n  /** Maximum number in range (omitted by the API for some entries) */\n  numberMax?: string;\n  /** Postal code (CEP), returned formatted with hyphen (e.g. \"01310-100\") */\n  postalCode: string;\n  /** Country code (ISO 3166-1 alpha-3, e.g. \"BRA\") */\n  country: string;\n}\n\n/**\n * Raw response envelope from the postal-code lookup endpoint\n * (`GET /v2/addresses/{cep}`). The API wraps the single result in an `address` key;\n * {@link AddressesResource.lookupByPostalCode} unwraps it and returns the inner\n * {@link Address}.\n */\nexport interface AddressLookupResponse {\n  /** The single matching address */\n  address: Address;\n}\n\n// ============================================================================\n// API Response Types\n// ============================================================================\n\nexport interface ListResponse<T> {\n  /** Response data array */\n  data: T[];\n  /** Total count (if available) */\n  totalCount?: number;\n  /** Page information */\n  page?: PageInfo;\n}\n\nexport interface PageInfo {\n  /** Current page index (1-based — the first page is 1) */\n  pageIndex: number;\n  /** Items per page */\n  pageCount: number;\n  /** Has next page */\n  hasNext?: boolean;\n  /** Has previous page */\n  hasPrevious?: boolean;\n}\n\nexport interface PaginationOptions extends Record<string, unknown> {\n  /** Page index (1-based — the first page is 1; the API rejects 0) */\n  pageIndex?: number;\n  /** Items per page */\n  pageCount?: number;\n}\n\n// ============================================================================\n// Polling Types\n// ============================================================================\n\nexport interface PollOptions {\n  /** Maximum number of polling attempts */\n  maxAttempts?: number;\n  /** Interval between attempts in milliseconds */\n  intervalMs?: number;\n}\n\n// ============================================================================\n// Utility Types\n// ============================================================================\n\n/**\n * Internal normalized configuration after processing NfeConfig.\n * API keys remain optional since validation is done lazily when resources are accessed.\n */\nexport interface RequiredNfeConfig {\n  /** Main API key (may be undefined if only using data services) */\n  apiKey: string | undefined;\n  /** Data API key for the lookup hosts (address, CNPJ, CPF, invoice query). Not valid on fiscal hosts. May be undefined; falls back to apiKey. */\n  dataApiKey: string | undefined;\n  /** Environment */\n  environment: 'production' | 'development';\n  /** Base URL for main API */\n  baseUrl: string;\n  /** Request timeout */\n  timeout: number;\n  /** Retry configuration */\n  retryConfig: Required<RetryConfig>;\n}\n\n/** Extract resource ID from response or input */\nexport type ResourceId = string;\n\n/** Generic API error response */\nexport interface ApiErrorResponse {\n  code: number;\n  message: string;\n  details?: unknown;\n}\n\n// ============================================================================\n// Service Invoice Type Exports from Generated Schema\n// ============================================================================\n\n// Import the operations type from generated spec\nimport type { operations } from '../generated/nf-servico-v1.js';\n\n// Re-export ServiceInvoice operation types for convenience\nexport type ServiceInvoicesGetOperation = operations['ServiceInvoices_Get'];\nexport type ServiceInvoicesPostOperation = operations['ServiceInvoices_Post'];\nexport type ServiceInvoicesGetByIdOperation = operations['ServiceInvoices_idGet'];\nexport type ServiceInvoicesDeleteOperation = operations['ServiceInvoices_Delete'];\nexport type ServiceInvoicesSendEmailOperation = operations['ServiceInvoices_SendEmail'];\nexport type ServiceInvoicesGetPdfOperation = operations['ServiceInvoices_GetDocumentPdf'];\nexport type ServiceInvoicesGetXmlOperation = operations['ServiceInvoices_GetDocumentXml'];\n\n/**\n * Service Invoice response type (from GET operations)\n * The main type representing a Service Invoice in the system\n */\nexport type ServiceInvoiceData =\n  NonNullable<\n    NonNullable<\n      ServiceInvoicesGetOperation['responses']['200']['content']['application/json']['serviceInvoices']\n    >[number]\n  >;\n\n/**\n * Service Invoice creation request body\n * Type for the data sent when creating a new service invoice\n */\nexport type CreateServiceInvoiceData =\n  ServiceInvoicesPostOperation['requestBody']['content']['application/json'];\n\n/**\n * Service Invoice list response\n * Type for the complete list response including metadata\n */\nexport type ServiceInvoiceListResponse =\n  ServiceInvoicesGetOperation['responses']['200']['content']['application/json'];\n\n/**\n * Service Invoice single item response\n * Type for a single invoice retrieval\n */\nexport type ServiceInvoiceSingleResponse =\n  ServiceInvoicesGetByIdOperation['responses']['200']['content']['application/json'];\n\n// Backward compatibility aliases\nexport type { ServiceInvoiceData as ServiceInvoice };\n\n// TODO: Add proper type exports when implementing other resources\n/**\n * Company entity.\n *\n * Additive enrichment (no breaking change, ships in a minor): the original\n * required fields and the permissive `[key: string]: unknown` index are kept,\n * and the documented `contribuintes-v2` fields (address, taxRegime, tradeName,\n * stateTaxes, …) are added as **optional** — so autocomplete improves without\n * tightening the type or the `create()` input. Use {@link CompanyResourceItem} /\n * {@link CompanyResourceV1} for the strict spec shapes, and\n * {@link CreateCompanyResourceItem} for a strict create input.\n */\nexport type Company = {\n  id?: string;\n  name: string;\n  federalTaxNumber: number;\n  email: string;\n} & Partial<Omit<CompanyResourceItem, 'id' | 'name' | 'federalTaxNumber' | 'email'>> & {\n    [key: string]: unknown;\n  };\n\n/**\n * Legal Person type.\n * NOTE: no dedicated 3.x spec backs the company-scoped legalpeople sub-resource yet,\n * so this remains hand-typed (review F14). Keep the permissive index for compat.\n */\nexport type LegalPerson = {\n  id?: string;\n  federalTaxNumber: string;\n  name: string;\n  [key: string]: unknown;\n};\n\n/**\n * Natural Person type.\n * NOTE: hand-typed for the same reason as {@link LegalPerson}.\n */\nexport type NaturalPerson = {\n  id?: string;\n  federalTaxNumber: string;\n  name: string;\n  [key: string]: unknown;\n};\n\n// ============================================================================\n// CT-e (Transportation Invoice) Types\n// ============================================================================\n\n// Import the components type from generated spec\nimport type { components as CteComponents } from '../generated/consulta-cte-v2.js';\n\n// ----------------------------------------------------------------------------\n// RTC (Reforma Tributária do Consumo) request types — from the dedicated specs\n// ----------------------------------------------------------------------------\nimport type { components as ServiceInvoiceRtcComponents } from '../generated/service-invoice-rtc-v1.js';\nimport type { components as ProductInvoiceRtcComponents } from '../generated/product-invoice-rtc-v1.js';\n\n/** RTC NFS-e (service) emission request body — named schema `NFSeRequest`. */\nexport type NFSeRtcRequest = ServiceInvoiceRtcComponents['schemas']['NFSeRequest'];\n\n/** RTC NF-e/NFC-e (product) emission request body — named schema `ProductInvoiceRequest`. */\nexport type ProductInvoiceRtcRequest =\n  ProductInvoiceRtcComponents['schemas']['ProductInvoiceRequest'];\n\n// ----------------------------------------------------------------------------\n// Empresas (contribuintes-v2) — spec-backed company/certificate/address types.\n// Clean public aliases over the .NET-qualified generated keys (same pattern as\n// CteComponents above). Full key-normalization remains a pipeline task (1.2).\n// ----------------------------------------------------------------------------\nimport type { components as ContribuintesComponents } from '../generated/contribuintes-v2.js';\n\n/** Company entity (list/item shape) — `contribuintes-v2` field-bearing schema. */\nexport type CompanyResourceItem =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.CompanyResourceItem'];\n\n/** Company entity (rich v1 shape, 28 fields). */\nexport type CompanyResourceV1 =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.CompanyResourceV1'];\n\n/** Company creation request body (opt-in, decoupled from the response type). */\nexport type CreateCompanyResourceItem =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.CreateCompanyResourceItem'];\n\n/** Company update request body. */\nexport type UpdateCompanyResourceItem =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.UpdateCompanyResourceItem'];\n\n/**\n * Options for the v2 cursor-based company listing\n * (`GET api.nfse.io/v2/companies`, contribuintes-v2).\n */\nexport interface CompanyV2ListOptions {\n  /** Cursor: start after this company ID */\n  startingAfter?: string;\n  /** Cursor: end before this company ID */\n  endingBefore?: string;\n  /** Number of results per page — the API accepts 1-50 (default: 10) */\n  limit?: number;\n}\n\n/**\n * Response of the v2 cursor-based company listing.\n *\n * Items follow the v2 projection ({@link CompanyResourceItem}) — a different\n * shape from the v1 {@link Company}: no NFS-e config fields (`rpsNumber`,\n * `issRate`, `environment`, `fiscalStatus`, `certificate`, ...), and with\n * v2-only fields (`stateTaxes`, `municipalTaxes`, `type`, `version`).\n */\nexport interface CompanyV2ListResponse {\n  /** Companies in this page (v2 projection) */\n  data: CompanyResourceItem[];\n  /** Whether more pages exist after this one */\n  hasMore: boolean;\n}\n\n/**\n * Certificado embutido no item da listagem de empresas v1.\n *\n * `GET /v1/companies` devolve este objeto em CADA item — medido em 2026-09-02\n * nos 50 itens da primeira página. É por isso que a varredura de certificados\n * por conta não precisa de uma requisição por empresa.\n *\n * Atenção ao nome do campo de vencimento: aqui é `expiresOn`; no endpoint\n * `/v1/companies/{id}/certificate` o mesmo dado se chama `validUntil`.\n */\nexport type CompanyCertificateV1 =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.CompanyCertificateV1'];\n\n/** Item de certificado devolvido por `/v1/companies/{id}/certificate`. */\nexport type CertificateMetadataResourceItem =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.CertificateMetadataResourceItem'];\n\n/** Situação do certificado: `None` | `Active` | `Inactive` | `Overdue` | `Pending`. */\nexport type CertificateStatus =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Domain.Entities.CertificateStatus'];\n\n/** Digital certificate metadata (real, spec-backed). */\nexport type CertificateMetadataResource =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.CertificateMetadataResource'];\n\n/** Digital certificate metadata collection (plural `/certificates`). */\nexport type CertificatesMetadataResource =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.CertificatesMetadataResource'];\n\n/** Company address (spec-backed). */\nexport type CompanyAddress =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.AddressResource'];\n\n/** Municipal tax registration (Inscrição Municipal) entity. */\nexport type MunicipalTax =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.MunicipalTaxResourceItem'];\n\n/** Municipal tax creation input (item; wrapped as `{ municipalTax }` on the wire). */\nexport type CreateMunicipalTaxData =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.CreateMunicipalTaxResourceItem'];\n\n/** Municipal tax update input (item). */\nexport type UpdateMunicipalTaxData =\n  ContribuintesComponents['schemas']['DFeTech.TaxPayers.Resources.UpdateMunicipalTaxResourceItem'];\n\n/** List response for municipal taxes (best-effort shape). */\nexport interface MunicipalTaxListResponse {\n  municipalTaxes?: MunicipalTax[];\n  [key: string]: unknown;\n}\n\n// ----------------------------------------------------------------------------\n// Consumer invoices (NFC-e) emission — from nf-consumidor-v2 named schemas.\n// ----------------------------------------------------------------------------\nimport type { components as NfConsumidorComponents } from '../generated/nf-consumidor-v2.js';\n\n/** NFC-e emission request body (`ConsumerInvoiceRequest`). */\nexport type ConsumerInvoiceData = NfConsumidorComponents['schemas']['ConsumerInvoiceRequest'];\n\n/** NFC-e invoice entity (`InvoiceResource`). */\nexport type ConsumerInvoice = NfConsumidorComponents['schemas']['InvoiceResource'];\n\n/** NFC-e list response envelope (`ConsumerInvoicesResource`). */\nexport type ConsumerInvoiceListResponse =\n  NfConsumidorComponents['schemas']['ConsumerInvoicesResource'];\n\n/** NFC-e disablement (inutilização) request body (`DisablementResource`). */\nexport type ConsumerInvoiceDisablementData =\n  NfConsumidorComponents['schemas']['DisablementResource'];\n\n/**\n * NFC-e items response (`InvoiceItemsResource`) — `{ accountId, companyId, id,\n * items, hasMore }`. Cursor pagination via `limit`/`startingAfter`.\n */\nexport type ConsumerInvoiceItemsResponse =\n  NfConsumidorComponents['schemas']['InvoiceItemsResource'];\n\n/**\n * NFC-e events response (`InvoiceEventsResource`) — `{ id, accountId, companyId,\n * events, hasMore }`. Its own type: the product-invoice events envelope is a\n * different shape and must not be reused here.\n */\nexport type ConsumerInvoiceEventsResponse =\n  NfConsumidorComponents['schemas']['InvoiceEventsResource'];\n\n/**\n * NFC-e cancellation response (`RequestCancellationResource`) — returned by\n * `DELETE /consumerinvoices/{id}` (204).\n */\nexport type ConsumerInvoiceCancellationResponse =\n  NfConsumidorComponents['schemas']['RequestCancellationResource'];\n\n/**\n * NFC-e document download response (`FileResource`) — `{ uri }`.\n *\n * Note the envelope differs from the inbound routes, which use\n * `publicTemporaryUri` ({@link InboundFileResource}). Verified live 2026-09-01.\n */\nexport type ConsumerInvoiceFileResource =\n  NfConsumidorComponents['schemas']['FileResource'];\n\n/**\n * Transportation Invoice inbound settings\n * Configuration for automatic CT-e search via SEFAZ Distribuição DFe\n */\nexport type TransportationInvoiceInboundSettings =\n  CteComponents['schemas']['DFe.NetCore.Domain.Resources.TransportationInvoiceInboundResource'];\n\n/**\n * Transportation Invoice metadata\n * Metadata of a CT-e document retrieved via Distribuição DFe\n */\nexport type TransportationInvoiceMetadata =\n  CteComponents['schemas']['DFe.NetCore.Domain.Resources.MetadataResource'];\n\n/**\n * Options for enabling automatic CT-e search\n */\nexport interface EnableTransportationInvoiceOptions {\n  /** Start from a specific NSU (Número Sequencial Único) */\n  startFromNsu?: number;\n  /** Start from a specific date (ISO 8601 format) */\n  startFromDate?: string;\n}\n\n/**\n * CT-e entity status\n */\nexport type TransportationInvoiceEntityStatus =\n  CteComponents['schemas']['DFe.NetCore.Domain.Enums.EntityStatus'];\n\n/**\n * CT-e metadata resource type\n */\nexport type TransportationInvoiceMetadataType =\n  CteComponents['schemas']['DFe.NetCore.Domain.Enums.MetadataResourceType'];\n\n// ============================================================================\n// Inbound NF-e Distribution Types\n// ============================================================================\n\n/**\n * Company reference in inbound document metadata\n */\nexport interface InboundCompany {\n  /** Company ID */\n  id: string;\n  /** Company CNPJ */\n  federalTaxNumber: string;\n}\n\n/**\n * Issuer reference in inbound document metadata\n */\nexport interface InboundIssuer {\n  /** Issuer CNPJ */\n  federalTaxNumber: string;\n  /** Issuer name */\n  name: string;\n}\n\n/**\n * Buyer reference in inbound document metadata\n */\nexport interface InboundBuyer {\n  /** Buyer CNPJ/CPF */\n  federalTaxNumber: string;\n  /** Buyer name */\n  name: string;\n}\n\n/**\n * Transportation entity reference in inbound document metadata\n */\nexport interface InboundTransportation {\n  /** Transportation CNPJ */\n  federalTaxNumber: string;\n  /** Transportation name */\n  name: string;\n}\n\n/**\n * Document download links\n */\nexport interface InboundLinks {\n  /** XML download URL */\n  xml: string;\n  /** PDF download URL */\n  pdf: string;\n}\n\n/**\n * Product invoice reference (used in webhook v2 responses)\n */\nexport interface InboundProductInvoice {\n  /** Access key of the referenced product invoice */\n  accessKey: string;\n}\n\n/**\n * Automatic manifesting configuration\n */\nexport interface AutomaticManifesting {\n  /** Minutes to wait before automatic awareness operation */\n  minutesToWaitAwarenessOperation: string;\n}\n\n/**\n * Inbound invoice metadata (webhook v1 format)\n *\n * Contains details of an NF-e or CT-e document retrieved via Distribuição DFe.\n * Corresponds to the generic endpoint `GET /{access_key}`.\n */\nexport interface InboundInvoiceMetadata {\n  /** Document ID */\n  id: string;\n  /** Creation timestamp */\n  createdOn: string;\n  /** 44-digit access key */\n  accessKey: string;\n  /** Parent document access key (for events) */\n  parentAccessKey: string;\n  /** Company that received the document */\n  company: InboundCompany;\n  /** Document issuer */\n  issuer: InboundIssuer;\n  /** Document buyer */\n  buyer: InboundBuyer;\n  /** Transportation entity */\n  transportation: InboundTransportation;\n  /** Download links */\n  links: InboundLinks;\n  /** XML download URL */\n  xmlUrl: string;\n  /** Sender CNPJ */\n  federalTaxNumberSender: string;\n  /** Sender name */\n  nameSender: string;\n  /** Document type */\n  type: string | null;\n  /** NSU (Número Sequencial Único) */\n  nsu: string;\n  /** Parent NSU */\n  nsuParent: string;\n  /** NF-e number */\n  nfeNumber: string;\n  /** NF-e serial number */\n  nfeSerialNumber: string;\n  /** Issue date */\n  issuedOn: string;\n  /** Document description */\n  description: string;\n  /** Total invoice amount */\n  totalInvoiceAmount: string;\n  /** Operation type */\n  operationType: string | null;\n}\n\n/**\n * Inbound product invoice metadata (webhook v2 format)\n *\n * Extends the base metadata with product invoice references.\n * Corresponds to the `GET /productinvoice/{access_key}` endpoint.\n */\nexport interface InboundProductInvoiceMetadata extends Omit<InboundInvoiceMetadata, 'nsuParent' | 'nfeSerialNumber' | 'operationType'> {\n  /** Referenced product invoices */\n  productInvoices: InboundProductInvoice[];\n}\n\n/**\n * Inbound NF-e distribution service settings\n *\n * Configuration for automatic NF-e search via SEFAZ Distribuição DFe.\n */\nexport interface InboundSettings {\n  /** Starting NSU for document retrieval */\n  startFromNsu: string;\n  /** Starting date for document retrieval */\n  startFromDate: string;\n  /** SEFAZ environment (e.g., Production) */\n  environmentSEFAZ: string | null;\n  /** Automatic manifesting configuration */\n  automaticManifesting: AutomaticManifesting;\n  /** Webhook version */\n  webhookVersion: string;\n  /** Company ID */\n  companyId: string;\n  /** Service status */\n  status: string | null;\n  /** Creation timestamp */\n  createdOn: string;\n  /** Last modification timestamp */\n  modifiedOn: string;\n}\n\n/**\n * Options for enabling automatic NF-e distribution fetch\n */\nexport interface EnableInboundOptions {\n  /** Starting NSU number */\n  startFromNsu?: string;\n  /** Starting date (ISO 8601 format) */\n  startFromDate?: string;\n  /** SEFAZ environment */\n  environmentSEFAZ?: string;\n  /** Automatic manifesting settings */\n  automaticManifesting?: AutomaticManifesting;\n  /** Webhook version */\n  webhookVersion?: string;\n}\n\n/**\n * Manifest event types for Manifestação do Destinatário\n *\n * - `210210` — Ciência da Operação (awareness of the operation)\n * - `210220` — Confirmação da Operação (confirmation of the operation)\n * - `210240` — Operação não Realizada (operation not performed)\n */\nexport type ManifestEventType = 210210 | 210220 | 210240;\n\n// ============================================================================\n// Product Invoice Query Types (consulta-nf)\n// ============================================================================\n\n// Enum string unions\n// ----------------------------------------------------------------------------\n\n/** Current status of a product invoice (NF-e) */\nexport type ProductInvoiceStatus = 'unknown' | 'authorized' | 'canceled';\n\n/** Payment type indicator */\nexport type ProductInvoicePaymentType = 'inCash' | 'term' | 'others';\n\n/** Operation type (incoming/outgoing) */\nexport type ProductInvoiceOperationType = 'incoming' | 'outgoing';\n\n/** Destination of the operation */\nexport type ProductInvoiceDestination = 'international_Operation' | 'interstate_Operation' | 'internal_Operation';\n\n/** DANFE print format */\nexport type ProductInvoicePrintType = 'none' | 'nFeNormalPortrait' | 'nFeNormalLandscape' | 'nFeSimplified' | 'dANFE_NFC_E' | 'dANFE_NFC_E_MSG_ELETRONICA';\n\n/** Invoice issue type (emission contingency modes) */\nexport type ProductInvoiceIssueType = 'normal' | 'cONTINGENCIA_OFF_LINE_NFC_E' | 'cONTINGENCIA_SVC_RS' | 'cONTINGENCIA_SVC_AN' | 'cONTINGENCIA_FS_DA' | 'cONTINGENCIA_DPEC' | 'cONTINGENCIA_SCAN' | 'cONTINGENCIA_FS_IA';\n\n/** Environment type */\nexport type ProductInvoiceEnvironmentType = 'production' | 'test';\n\n/** Invoice purpose */\nexport type ProductInvoicePurposeType = 'normal' | 'complement' | 'adjustment' | 'devolution';\n\n/** Consumer type */\nexport type ProductInvoiceConsumerType = 'normal' | 'finalConsumer';\n\n/** Buyer presence indicator */\nexport type ProductInvoicePresenceType = 'none' | 'presence' | 'internet' | 'telephone' | 'delivery' | 'presenceOutOfStore' | 'othersNoPresente';\n\n/** Process type for invoice emission */\nexport type ProductInvoiceProcessType = 'ownSoftware' | 'fiscoSingle' | 'taxPayerSingle' | 'fiscoSoftware';\n\n/** Tax regime code */\nexport type ProductInvoiceTaxRegimeCode = 'national_Simple' | 'national_Simple_Brute' | 'normal_Regime';\n\n/** Person type */\nexport type ProductInvoicePersonType = 'undefined' | 'naturalPerson' | 'legalEntity';\n\n/** Payment method */\nexport type ProductInvoicePaymentMethod = 'cash' | 'cheque' | 'creditCard' | 'debitCard' | 'storeCredict' | 'foodVouchers' | 'mealVouchers' | 'giftVouchers' | 'fuelVouchers' | 'commercialDuplicate' | 'bankSlip' | 'unpaid' | 'others';\n\n/** Card flag/brand */\nexport type ProductInvoiceCardFlag = 'visa' | 'mastercard' | 'americanExpress' | 'sorocred' | 'dinnersClub' | 'elo' | 'hipercard' | 'aura' | 'cabal' | 'outros';\n\n/** Integration payment type */\nexport type ProductInvoiceIntegrationPaymentType = 'integrated' | 'notIntegrated';\n\n// Nested types\n// ----------------------------------------------------------------------------\n\n/** City within an address */\nexport interface ProductInvoiceCity {\n  code?: string;\n  name?: string;\n}\n\n/** Address for issuer or buyer */\nexport interface ProductInvoiceAddress {\n  phone?: string;\n  state?: string;\n  city?: ProductInvoiceCity;\n  district?: string;\n  additionalInformation?: string;\n  streetSuffix?: string;\n  street?: string;\n  number?: string;\n  postalCode?: string;\n  country?: string;\n}\n\n/** Invoice issuer (emitente) */\nexport interface ProductInvoiceIssuer {\n  federalTaxNumber?: number;\n  name?: string;\n  tradeName?: string;\n  address?: ProductInvoiceAddress;\n  stateTaxNumber?: string;\n  codeTaxRegime?: ProductInvoiceTaxRegimeCode;\n  cnae?: number;\n  im?: string;\n  iest?: number;\n  type?: ProductInvoicePersonType;\n}\n\n/** Invoice buyer (destinatário) */\nexport interface ProductInvoiceBuyer {\n  federalTaxNumber?: number;\n  name?: string;\n  address?: ProductInvoiceAddress;\n  stateTaxNumber?: string;\n  stateTaxNumberIndicator?: number;\n  email?: string;\n  type?: ProductInvoicePersonType;\n}\n\n/** ICMS totals */\nexport interface ProductInvoiceIcmsTotals {\n  baseTax?: number;\n  icmsAmount?: number;\n  icmsExemptAmount?: number;\n  stCalculationBasisAmount?: number;\n  stAmount?: number;\n  productAmount?: number;\n  freightAmount?: number;\n  insuranceAmount?: number;\n  discountAmount?: number;\n  iiAmount?: number;\n  ipiAmount?: number;\n  pisAmount?: number;\n  cofinsAmount?: number;\n  othersAmount?: number;\n  invoiceAmount?: number;\n  fcpufDestinationAmount?: number;\n  icmsufDestinationAmount?: number;\n  icmsufSenderAmount?: number;\n  federalTaxesAmount?: number;\n  fcpAmount?: number;\n  fcpstAmount?: number;\n  fcpstRetAmount?: number;\n  ipiDevolAmount?: number;\n}\n\n/** ISSQN totals */\nexport interface ProductInvoiceIssqnTotals {\n  totalServiceNotTaxedICMS?: number;\n  baseRateISS?: number;\n  totalISS?: number;\n  valueServicePIS?: number;\n  valueServiceCOFINS?: number;\n  provisionService?: string;\n  deductionReductionBC?: number;\n  valueOtherRetention?: number;\n  discountUnconditional?: number;\n  discountConditioning?: number;\n  totalRetentionISS?: number;\n  codeTaxRegime?: number;\n}\n\n/** Invoice totals */\nexport interface ProductInvoiceTotals {\n  icms?: ProductInvoiceIcmsTotals;\n  issqn?: ProductInvoiceIssqnTotals;\n}\n\n/** ICMS tax on item */\nexport interface ProductInvoiceItemIcms {\n  origin?: string;\n  cst?: string;\n  baseTaxModality?: string;\n  baseTax?: number;\n  baseTaxSTModality?: string;\n  baseTaxSTReduction?: number;\n  baseTaxSTAmount?: number;\n  baseTaxReduction?: number;\n  stRate?: number;\n  stAmount?: number;\n  stMarginAmount?: number;\n  csosn?: string;\n  rate?: number;\n  amount?: number;\n  snCreditRate?: string;\n  snCreditAmount?: string;\n  stMarginAddedAmount?: string;\n  stRetentionAmount?: string;\n  baseSTRetentionAmount?: string;\n  baseTaxOperationPercentual?: string;\n  ufst?: string;\n  amountSTUnfounded?: number;\n  amountSTReason?: string;\n  baseSNRetentionAmount?: string;\n  snRetentionAmount?: string;\n  amountOperation?: string;\n  percentualDeferment?: string;\n  baseDeferred?: string;\n  fcpRate?: number;\n  fcpAmount?: number;\n  fcpstRate?: number;\n  fcpstAmount?: number;\n  fcpstRetRate?: number;\n  fcpstRetAmount?: number;\n  bcfcpstAmount?: number;\n  finalConsumerRate?: number;\n  bcstRetIssuerAmount?: number;\n  stRetIssuerAmout?: number;\n  bcstBuyerAmount?: number;\n  stBuyerAmout?: number;\n  substituteAmount?: number;\n}\n\n/** IPI tax on item */\nexport interface ProductInvoiceItemIpi {\n  classification?: string;\n  producerCNPJ?: string;\n  stampCode?: string;\n  stampQuantity?: number;\n  classificationCode?: string;\n  cst?: string;\n  base?: string;\n  rate?: number;\n  unitQuantity?: number;\n  unitAmount?: number;\n  amount?: number;\n}\n\n/** Import tax (II) on item */\nexport interface ProductInvoiceItemII {\n  baseTax?: string;\n  customsExpenditureAmount?: string;\n  amount?: number;\n  iofAmount?: number;\n}\n\n/** PIS tax on item */\nexport interface ProductInvoiceItemPis {\n  cst?: string;\n  baseTax?: number;\n  rate?: number;\n  amount?: number;\n  baseTaxProductQuantity?: number;\n  productRate?: number;\n}\n\n/** COFINS tax on item */\nexport interface ProductInvoiceItemCofins {\n  cst?: string;\n  baseTax?: number;\n  rate?: number;\n  amount?: number;\n  baseTaxProductQuantity?: number;\n  productRate?: number;\n}\n\n/** ICMS destination (interestadual) on item */\nexport interface ProductInvoiceItemIcmsDestination {\n  vBCUFDest?: number;\n  pFCPUFDest?: number;\n  pICMSUFDest?: number;\n  pICMSInter?: number;\n  pICMSInterPart?: number;\n  vFCPUFDest?: number;\n  vICMSUFDest?: number;\n  vICMSUFRemet?: number;\n  vBCFCPUFDest?: number;\n}\n\n/** Tax group on item */\nexport interface ProductInvoiceItemTax {\n  totalTax?: number;\n  icms?: ProductInvoiceItemIcms;\n  ipi?: ProductInvoiceItemIpi;\n  ii?: ProductInvoiceItemII;\n  pis?: ProductInvoiceItemPis;\n  cofins?: ProductInvoiceItemCofins;\n  icmsDestination?: ProductInvoiceItemIcmsDestination;\n}\n\n/** Medicine detail on item */\nexport interface ProductInvoiceItemMedicine {\n  maximumPrice?: number;\n  anvisaCode?: string;\n  batchId?: string;\n  batchQuantity?: number;\n  manufacturedOn?: string;\n  expireOn?: string;\n}\n\n/** Fuel CIDE information */\nexport interface ProductInvoiceItemFuelCide {\n  bc?: number;\n  rate?: number;\n  cideAmount?: number;\n}\n\n/** Fuel pump (encerrante) information */\nexport interface ProductInvoiceItemFuelPump {\n  spoutNumber?: number;\n  number?: number;\n  tankNumber?: number;\n  beginningAmount?: number;\n  endAmount?: number;\n}\n\n/** Fuel detail on item */\nexport interface ProductInvoiceItemFuel {\n  codeANP?: string;\n  percentageNG?: number;\n  descriptionANP?: string;\n  percentageGLP?: number;\n  percentageNGn?: number;\n  percentageGNi?: number;\n  startingAmount?: number;\n  codif?: string;\n  amountTemp?: number;\n  stateBuyer?: string;\n  cide?: ProductInvoiceItemFuelCide;\n  pump?: ProductInvoiceItemFuelPump;\n}\n\n/** Invoice item (product/service) */\nexport interface ProductInvoiceItem {\n  code?: string;\n  codeGTIN?: string;\n  description?: string;\n  ncm?: string;\n  extipi?: string;\n  cfop?: number;\n  unit?: string;\n  quantity?: number;\n  unitAmount?: number;\n  totalAmount?: number;\n  eanTaxableCode?: string;\n  unitTax?: string;\n  quantityTax?: number;\n  taxUnitAmount?: number;\n  freightAmount?: number;\n  insuranceAmount?: number;\n  discountAmount?: number;\n  othersAmount?: number;\n  totalIndicator?: boolean;\n  cest?: string;\n  tax?: ProductInvoiceItemTax;\n  additionalInformation?: string;\n  numberOrderBuy?: string;\n  itemNumberOrderBuy?: number;\n  medicineDetail?: ProductInvoiceItemMedicine;\n  fuel?: ProductInvoiceItemFuel;\n}\n\n/** Transport group (transportador) */\nexport interface ProductInvoiceTransportGroup {\n  cityName?: string;\n  federalTaxNumber?: string;\n  cpf?: string;\n  name?: string;\n  stateTaxNumber?: string;\n  fullAddress?: string;\n  state?: string;\n  transportRetention?: string;\n}\n\n/** Transport reboque (trailer) */\nexport interface ProductInvoiceTransportReboque {\n  plate?: string;\n  uf?: string;\n  rntc?: string;\n  wagon?: string;\n  ferry?: string;\n}\n\n/** Transport volume */\nexport interface ProductInvoiceTransportVolume {\n  volumeQuantity?: number;\n  species?: string;\n  brand?: string;\n  volumeNumeration?: string;\n  netWeight?: number;\n  grossWeight?: number;\n}\n\n/** Transport vehicle */\nexport interface ProductInvoiceTransportVehicle {\n  plate?: string;\n  state?: string;\n  rntc?: string;\n}\n\n/** Transport ICMS retention */\nexport interface ProductInvoiceTransportRate {\n  serviceAmount?: number;\n  bcRetentionAmount?: number;\n  icmsRetentionRate?: number;\n  icmsRetentionAmount?: number;\n  cfop?: number;\n  cityGeneratorFactCode?: number;\n}\n\n/** Transport information */\nexport interface ProductInvoiceTransport {\n  freightModality?: number;\n  transportGroup?: ProductInvoiceTransportGroup;\n  reboque?: ProductInvoiceTransportReboque;\n  volume?: ProductInvoiceTransportVolume;\n  transportVehicle?: ProductInvoiceTransportVehicle;\n  sealNumber?: string;\n  transpRate?: ProductInvoiceTransportRate;\n}\n\n/** Additional information */\nexport interface ProductInvoiceAdditionalInfo {\n  fisco?: string;\n  taxpayer?: string;\n  xmlAuthorized?: number[];\n  effort?: string;\n  order?: string;\n  contract?: string;\n  taxDocumentsReference?: ProductInvoiceTaxDocumentRef[];\n  taxpayerComments?: ProductInvoiceTaxpayerComment[];\n  referencedProcess?: ProductInvoiceReferencedProcess[];\n}\n\n/** Tax document reference */\nexport interface ProductInvoiceTaxDocumentRef {\n  taxCouponInformation?: {\n    modelDocumentFiscal?: string;\n    orderECF?: string;\n    orderCountOperation?: number;\n  };\n  documentInvoiceReference?: {\n    state?: number;\n    yearMonth?: string;\n    federalTaxNumber?: string;\n    model?: string;\n    series?: string;\n    number?: string;\n  };\n  accessKey?: string;\n}\n\n/** Taxpayer comment */\nexport interface ProductInvoiceTaxpayerComment {\n  field?: string;\n  text?: string;\n}\n\n/** Referenced process */\nexport interface ProductInvoiceReferencedProcess {\n  identifierConcessory?: string;\n  identifierOrigin?: number;\n}\n\n/** Protocol information */\nexport interface ProductInvoiceProtocol {\n  id?: string;\n  environmentType?: ProductInvoiceEnvironmentType;\n  applicationVersion?: string;\n  accessKey?: string;\n  receiptOn?: string;\n  protocolNumber?: string;\n  validatorDigit?: string;\n  statusCode?: number;\n  description?: string;\n  signature?: string;\n}\n\n/** Payment card details */\nexport interface ProductInvoicePaymentCard {\n  federalTaxNumber?: string;\n  flag?: ProductInvoiceCardFlag;\n  authorization?: string;\n  integrationPaymentType?: ProductInvoiceIntegrationPaymentType;\n}\n\n/** Payment detail entry */\nexport interface ProductInvoicePaymentDetail {\n  method?: ProductInvoicePaymentMethod;\n  amount?: number;\n  card?: ProductInvoicePaymentCard;\n}\n\n/** Payment group */\nexport interface ProductInvoicePayment {\n  paymentDetail?: ProductInvoicePaymentDetail[];\n  payBack?: number;\n}\n\n/** Billing bill (fatura) */\nexport interface ProductInvoiceBill {\n  number?: string;\n  originalAmount?: number;\n  discountAmount?: number;\n  netAmount?: number;\n}\n\n/** Billing duplicate */\nexport interface ProductInvoiceDuplicate {\n  duplicateNumber?: string;\n  expirationOn?: string;\n  amount?: number;\n}\n\n/** Billing information (cobrança) */\nexport interface ProductInvoiceBilling {\n  bill?: ProductInvoiceBill;\n  duplicates?: ProductInvoiceDuplicate[];\n}\n\n/** Full product invoice details returned by SEFAZ query */\nexport interface ProductInvoiceDetails {\n  currentStatus?: ProductInvoiceStatus;\n  stateCode?: number;\n  checkCode?: number;\n  operationNature?: string;\n  paymentType?: ProductInvoicePaymentType;\n  codeModel?: number;\n  serie?: number;\n  number?: number;\n  issuedOn?: string;\n  operationOn?: string;\n  operationType?: ProductInvoiceOperationType;\n  destination?: ProductInvoiceDestination;\n  cityCode?: number;\n  printType?: ProductInvoicePrintType;\n  issueType?: ProductInvoiceIssueType;\n  checkCodeDigit?: number;\n  environmentType?: ProductInvoiceEnvironmentType;\n  purposeType?: ProductInvoicePurposeType;\n  consumerType?: ProductInvoiceConsumerType;\n  presenceType?: ProductInvoicePresenceType;\n  processType?: ProductInvoiceProcessType;\n  invoiceVersion?: string;\n  xmlVersion?: string;\n  contingencyOn?: string;\n  contingencyJustification?: string;\n  issuer?: ProductInvoiceIssuer;\n  buyer?: ProductInvoiceBuyer;\n  totals?: ProductInvoiceTotals;\n  transport?: ProductInvoiceTransport;\n  additionalInformation?: ProductInvoiceAdditionalInfo;\n  protocol?: ProductInvoiceProtocol;\n  items?: ProductInvoiceItem[];\n  billing?: ProductInvoiceBilling;\n  payment?: ProductInvoicePayment[];\n}\n\n/** Fiscal event associated with a product invoice */\nexport interface ProductInvoiceEvent {\n  stateCode?: number;\n  type?: number;\n  sequence?: number;\n  authorFederalTaxNumber?: string;\n  id?: string;\n  protocol?: number;\n  authorizedOn?: string;\n  description?: string;\n}\n\n/** Response from listing fiscal events for a product invoice */\nexport interface ProductInvoiceEventsResponse {\n  events?: ProductInvoiceEvent[];\n  createdOn?: string;\n}\n\n// ============================================================================\n// Consumer Invoice Query Types (CFe-SAT / Cupom Fiscal Eletrônico)\n// ============================================================================\n\n/** Status of a CFe-SAT consumer invoice (coupon) */\nexport type CouponStatus = 'Unknown' | 'Authorized' | 'Canceled' | (string & {});\n\n/** Person type for CFe-SAT entities */\nexport type CouponPersonType = 'Undefined' | 'NaturalPerson' | 'LegalEntity' | (string & {});\n\n/** Tax regime for CFe-SAT issuer */\nexport type CouponTaxRegime = 'National_Simple' | 'National_Simple_Brute' | 'Normal_Regime' | (string & {});\n\n/** Payment method for CFe-SAT coupon */\nexport type CouponPaymentMethod =\n  | 'Cash'\n  | 'Cheque'\n  | 'CreditCard'\n  | 'DebitCard'\n  | 'StoreCredict'\n  | 'FoodVouchers'\n  | 'MealVouchers'\n  | 'GiftVouchers'\n  | 'FuelVouchers'\n  | 'CommercialDuplicate'\n  | 'BankSlip'\n  | 'BankDeposit'\n  | 'InstantPayment'\n  | 'WireTransfer'\n  | 'Cashback'\n  | 'Unpaid'\n  | 'Others'\n  | (string & {});\n\n/** ISSQN tax incentive indicator */\nexport type CouponIssqnTaxIncentive = 'Yes' | 'No' | (string & {});\n\n/** City reference in CFe-SAT */\nexport interface CouponCity {\n  code?: string;\n  name?: string;\n}\n\n/** Address in CFe-SAT documents */\nexport interface CouponAddress {\n  state?: string;\n  city?: CouponCity;\n  district?: string;\n  additionalInformation?: string;\n  streetSuffix?: string;\n  street?: string;\n  number?: string;\n  postalCode?: string;\n  country?: string;\n}\n\n/** Issuer (emit) of a CFe-SAT coupon */\nexport interface CouponIssuer {\n  federalTaxNumber?: number;\n  type?: CouponPersonType;\n  name?: string;\n  tradeName?: string;\n  address?: CouponAddress;\n  stateTaxNumber?: string;\n  taxRegime?: CouponTaxRegime;\n  municipalTaxNumber?: string;\n  iss?: string;\n  avarageIndicator?: boolean;\n}\n\n/** Buyer (dest) of a CFe-SAT coupon */\nexport interface CouponBuyer {\n  pretectedPersonalInformation?: string;\n  federalTaxNumber?: number;\n  name?: string;\n}\n\n/** ICMS totals for a CFe-SAT coupon */\nexport interface CouponIcmsTotal {\n  productAmount?: number;\n  discountAmount?: number;\n  othersAmount?: number;\n  icmsAmount?: number;\n  inputDiscountAmount?: number;\n  inputAdditionAmount?: number;\n  pisAmount?: number;\n  cofinsAmount?: number;\n  pisstAmount?: number;\n  cofinsstAmount?: number;\n}\n\n/** ISSQN totals for a CFe-SAT coupon */\nexport interface CouponIssqnTotal {\n  baseAmount?: number;\n  issAmount?: number;\n  pisAmount?: number;\n  cofinsAmount?: number;\n  pisstAmount?: number;\n  cofinsstAmount?: number;\n}\n\n/** Totals for a CFe-SAT coupon */\nexport interface CouponTotal {\n  icms?: CouponIcmsTotal;\n  issqn?: CouponIssqnTotal;\n  totalAmount?: number;\n  couponAmount?: number;\n}\n\n/** Tax base resource (used by PIS/COFINS ST) */\nexport interface CouponTaxBase {\n  baseTax?: number;\n  rate?: number;\n  amount?: number;\n  rateAmount?: number;\n  quantity?: number;\n}\n\n/** ICMS tax data for a coupon item */\nexport interface CouponIcmsTax {\n  origin?: string;\n  cst?: string;\n  csosn?: string;\n  amount?: number;\n  rate?: number;\n}\n\n/** PIS tax data for a coupon item */\nexport interface CouponPisTax {\n  cst?: string;\n  st?: CouponTaxBase;\n  baseTax?: number;\n  rate?: number;\n  amount?: number;\n  rateAmount?: number;\n  quantity?: number;\n}\n\n/** COFINS tax data for a coupon item */\nexport interface CouponCofinsTax {\n  cst?: string;\n  st?: CouponTaxBase;\n  baseTax?: number;\n  rate?: number;\n  amount?: number;\n  rateAmount?: number;\n  quantity?: number;\n}\n\n/** ISSQN tax data for a coupon item */\nexport interface CouponIssqnTax {\n  deductionsAmount?: number;\n  baseTax?: number;\n  rate?: number;\n  amount?: number;\n  federalServiceCode?: string;\n  cityServiceCode?: string;\n  cityCode?: number;\n  taxIncentive?: CouponIssqnTaxIncentive;\n  operationNature?: string;\n}\n\n/** Tax breakdown for a coupon item */\nexport interface CouponItemTax {\n  totalTax?: number;\n  icms?: CouponIcmsTax;\n  pis?: CouponPisTax;\n  cofins?: CouponCofinsTax;\n  issqn?: CouponIssqnTax;\n}\n\n/** Fisco observation field */\nexport interface CouponFiscoField {\n  key?: string;\n  value?: string;\n}\n\n/** Referenced tax document */\nexport interface CouponReferencedDocument {\n  accessKey?: string;\n  order?: number;\n}\n\n/** Product item in a CFe-SAT coupon */\nexport interface CouponItem {\n  description?: string;\n  quantity?: number;\n  unit?: string;\n  code?: string;\n  codeGTIN?: string;\n  ncm?: string;\n  cfop?: number;\n  cest?: string;\n  unitAmount?: number;\n  discountAmount?: number;\n  othersAmount?: number;\n  additionalInformation?: string;\n  itemNumberOrderBuy?: number;\n  netAmount?: number;\n  grossAmount?: number;\n  rule?: string;\n  apportionmentDiscountAmount?: number;\n  apportionmentAmount?: number;\n  fisco?: CouponFiscoField[];\n  tax?: CouponItemTax;\n}\n\n/** Payment detail in a CFe-SAT coupon */\nexport interface CouponPaymentDetail {\n  method?: CouponPaymentMethod;\n  amount?: number;\n  card?: string;\n}\n\n/** Payment group for a CFe-SAT coupon */\nexport interface CouponPayment {\n  payBack?: number;\n  paymentDetails?: CouponPaymentDetail[];\n}\n\n/** Delivery information for a CFe-SAT coupon */\nexport interface CouponDelivery {\n  address?: CouponAddress;\n}\n\n/** Additional information for a CFe-SAT coupon */\nexport interface CouponAdditionalInformation {\n  taxpayer?: string;\n  fisco?: CouponFiscoField[];\n  referencedDocuments?: CouponReferencedDocument[];\n}\n\n/** CFe-SAT tax coupon (Cupom Fiscal Eletrônico) */\nexport interface TaxCoupon {\n  currentStatus?: CouponStatus;\n  number?: number;\n  satSerie?: string;\n  softwareVersion?: string;\n  softwareFederalTaxNumber?: number;\n  accessKey?: string;\n  cashier?: number;\n  issuedOn?: string;\n  createdOn?: string;\n  xmlVersion?: string;\n  issuer?: CouponIssuer;\n  buyer?: CouponBuyer;\n  totals?: CouponTotal;\n  delivery?: CouponDelivery;\n  additionalInformation?: CouponAdditionalInformation;\n  items?: CouponItem[];\n  payment?: CouponPayment;\n}\n\n// ============================================================================\n// Legal Entity Lookup Types (consulta-cnpj)\n// ============================================================================\n\n/** Valid Brazilian state abbreviations (27 UFs + EX + NA) */\nexport type BrazilianState =\n  | 'AC' | 'AL' | 'AM' | 'AP' | 'BA' | 'CE' | 'DF' | 'ES' | 'GO'\n  | 'MA' | 'MG' | 'MS' | 'MT' | 'PA' | 'PB' | 'PE' | 'PI' | 'PR'\n  | 'RJ' | 'RN' | 'RO' | 'RR' | 'RS' | 'SC' | 'SE' | 'SP' | 'TO'\n  | 'EX' | 'NA';\n\n/** Options for basic info lookup */\nexport interface LegalEntityBasicInfoOptions {\n  /** Whether to update the address from postal service data (default: true) */\n  updateAddress?: boolean;\n  /** When updateAddress=false, whether to update only the city code from postal service data (default: false) */\n  updateCityCode?: boolean;\n}\n\n// --- Response Wrappers ---\n\n/** Response wrapper for CNPJ basic info lookup */\nexport interface LegalEntityBasicInfoResponse {\n  /** Legal entity data */\n  legalEntity?: LegalEntityBasicInfo;\n}\n\n/** Response wrapper for state tax info lookup */\nexport interface LegalEntityStateTaxResponse {\n  /** Legal entity state tax data */\n  legalEntity?: LegalEntityStateTaxInfo;\n}\n\n/** Response wrapper for state tax for invoice lookup */\nexport interface LegalEntityStateTaxForInvoiceResponse {\n  /** Legal entity state tax data for invoice evaluation */\n  legalEntity?: LegalEntityStateTaxForInvoiceInfo;\n}\n\n// --- Core Entity Types ---\n\n/** Company size classification */\nexport type LegalEntitySize = 'Unknown' | 'ME' | 'EPP' | 'DEMAIS';\n\n/** Company registration status */\nexport type LegalEntityStatus = 'Unknown' | 'Active' | 'Suspended' | 'Cancelled' | 'Unabled' | 'Null';\n\n/** Organizational unit type */\nexport type LegalEntityUnit = 'Headoffice' | 'Subsidiary';\n\n/** Tax regime code */\nexport type LegalEntityTaxRegime = 'Unknown' | 'SimplesNacional' | 'MEI' | 'Normal';\n\n/** Legal nature classification */\nexport type LegalEntityNatureCode =\n  | 'EmpresaPublica' | 'SociedadeEconomiaMista' | 'SociedadeAnonimaAberta'\n  | 'SociedadeAnonimaFechada' | 'SociedadeEmpresariaLimitada'\n  | 'SociedadeEmpresariaEmNomeColetivo' | 'SociedadeEmpresariaEmComanditaSimples'\n  | 'SociedadeEmpresariaEmComanditaporAcoes' | 'SociedadeemContaParticipacao'\n  | 'Empresario' | 'Cooperativa' | 'ConsorcioSociedades' | 'GrupoSociedades'\n  | 'EmpresaDomiciliadaExterior' | 'ClubeFundoInvestimento'\n  | 'SociedadeSimplesPura' | 'SociedadeSimplesLimitada'\n  | 'SociedadeSimplesEmNomeColetivo' | 'SociedadeSimplesEmComanditaSimples'\n  | 'EmpresaBinacional' | 'ConsorcioEmpregadores' | 'ConsorcioSimples'\n  | 'EireliNaturezaEmpresaria' | 'EireliNaturezaSimples' | 'ServicoNotarial'\n  | 'FundacaoPrivada' | 'ServicoSocialAutonomo' | 'CondominioEdilicio'\n  | 'ComissaoConciliacaoPrevia' | 'EntidadeMediacaoArbitragem'\n  | 'PartidoPolitico' | 'EntidadeSindical'\n  | 'EstabelecimentoBrasilFundacaoAssociacaoEstrangeiras'\n  | 'FundacaoAssociacaoDomiciliadaExterior' | 'OrganizacaoReligiosa'\n  | 'ComunidadeIndigena' | 'FundoPrivado' | 'AssociacaoPrivada'\n  | 'OutrasSemFimLucrativo' | 'Unknown';\n\n/** State tax registration status */\nexport type LegalEntityStateTaxStatus = 'Abled' | 'Unabled' | 'Cancelled' | 'Unknown';\n\n/** Extended state tax registration status for invoice evaluation */\nexport type LegalEntityStateTaxForInvoiceStatus =\n  | 'Abled' | 'Unabled' | 'Cancelled'\n  | 'UnabledTemp' | 'UnabledNotConfirmed'\n  | 'Unknown' | 'UnknownTemp' | 'UnknownNotConfirmed';\n\n/** Fiscal document contributor status */\nexport type LegalEntityFiscalDocumentStatus = 'Abled' | 'Unabled' | 'Unknown';\n\n/** Economic activity type classification */\nexport type LegalEntityActivityType = 'Main' | 'Secondary';\n\n/** Phone source */\nexport type LegalEntityPhoneSource = 'RFB';\n\n// --- Nested Object Types ---\n\n/** City information */\nexport interface LegalEntityCity {\n  /** City IBGE code */\n  code?: string;\n  /** City name */\n  name?: string;\n}\n\n/** Address from Legal Entity API */\nexport interface LegalEntityAddress {\n  /** State abbreviation (UF) */\n  state?: string;\n  /** City information */\n  city?: LegalEntityCity;\n  /** District / neighborhood */\n  district?: string;\n  /** Additional address information */\n  additionalInformation?: string;\n  /** Street suffix (type) */\n  streetSuffix?: string;\n  /** Street name */\n  street?: string;\n  /** Street number */\n  number?: string;\n  /** Minimum number range */\n  numberMin?: string;\n  /** Maximum number range */\n  numberMax?: string;\n  /** Postal code (CEP) */\n  postalCode?: string;\n  /** Country */\n  country?: string;\n}\n\n/** Phone number */\nexport interface LegalEntityPhone {\n  /** Area code (DDD) */\n  ddd?: string;\n  /** Phone number */\n  number?: string;\n  /** Information source */\n  source?: LegalEntityPhoneSource;\n}\n\n/** Economic activity (CNAE) */\nexport interface LegalEntityEconomicActivity {\n  /** Activity classification (Main or Secondary) */\n  type?: LegalEntityActivityType;\n  /** CNAE code */\n  code?: number;\n  /** CNAE description */\n  description?: string;\n}\n\n/** Legal nature */\nexport interface LegalEntityNature {\n  /** Legal nature code */\n  code?: string;\n  /** Legal nature description */\n  description?: string;\n}\n\n/** Partner qualification */\nexport interface LegalEntityQualification {\n  /** Qualification code */\n  code?: string;\n  /** Qualification description */\n  description?: string;\n}\n\n/** Company partner */\nexport interface LegalEntityPartner {\n  /** Partner name */\n  name?: string;\n  /** Partner qualification */\n  qualification?: LegalEntityQualification;\n}\n\n/** Fiscal document indicator (NFe/NFSe/CTe/NFCe) */\nexport interface LegalEntityFiscalDocumentInfo {\n  /** Contributor status */\n  status?: LegalEntityFiscalDocumentStatus;\n  /** Data source description */\n  description?: string;\n}\n\n/** State tax registration (Inscrição Estadual) */\nexport interface LegalEntityStateTax {\n  /** Registration status */\n  status?: LegalEntityStateTaxStatus;\n  /** State tax number (IE) */\n  taxNumber?: string;\n  /** Status date */\n  statusOn?: string;\n  /** Opening date */\n  openedOn?: string;\n  /** Closing date */\n  closedOn?: string;\n  /** Additional information */\n  additionalInformation?: string;\n  /** State code */\n  code?: BrazilianState;\n  /** Address */\n  address?: LegalEntityAddress;\n  /** Economic activities (CNAE) */\n  economicActivities?: LegalEntityEconomicActivity[];\n  /** NFe indicator */\n  nfe?: LegalEntityFiscalDocumentInfo;\n  /** NFSe indicator */\n  nfse?: LegalEntityFiscalDocumentInfo;\n  /** CTe indicator */\n  cte?: LegalEntityFiscalDocumentInfo;\n  /** NFCe indicator */\n  nfce?: LegalEntityFiscalDocumentInfo;\n}\n\n/** State tax registration for invoice evaluation (extended status) */\nexport interface LegalEntityStateTaxForInvoice {\n  /** Registration status (extended enum) */\n  status?: LegalEntityStateTaxForInvoiceStatus;\n  /** State tax number (IE) */\n  taxNumber?: string;\n  /** Status date */\n  statusOn?: string;\n  /** Opening date */\n  openedOn?: string;\n  /** Closing date */\n  closedOn?: string;\n  /** Additional information */\n  additionalInformation?: string;\n  /** State code */\n  code?: BrazilianState;\n  /** Address */\n  address?: LegalEntityAddress;\n  /** Economic activities (CNAE) */\n  economicActivities?: LegalEntityEconomicActivity[];\n  /** NFe indicator */\n  nfe?: LegalEntityFiscalDocumentInfo;\n  /** NFSe indicator */\n  nfse?: LegalEntityFiscalDocumentInfo;\n  /** CTe indicator */\n  cte?: LegalEntityFiscalDocumentInfo;\n  /** NFCe indicator */\n  nfce?: LegalEntityFiscalDocumentInfo;\n}\n\n// --- Main Entity Types ---\n\n/** Full company data from CNPJ basic info lookup */\nexport interface LegalEntityBasicInfo {\n  /** Trade name (nome fantasia) */\n  tradeName?: string;\n  /** Legal name (razão social) */\n  name?: string;\n  /** Federal tax number (CNPJ) — numeric */\n  federalTaxNumber?: number;\n  /** Company size classification */\n  size?: LegalEntitySize;\n  /** Opening date */\n  openedOn?: string;\n  /** Company address */\n  address?: LegalEntityAddress;\n  /** Phone numbers */\n  phones?: LegalEntityPhone[];\n  /** Registration status date */\n  statusOn?: string;\n  /** Registration status */\n  status?: LegalEntityStatus;\n  /** Email address */\n  email?: string;\n  /** Responsible federal entity (EFR) */\n  responsableEntity?: string;\n  /** Special status */\n  specialStatus?: string;\n  /** Special status date */\n  specialStatusOn?: string;\n  /** Query date (when the data was fetched) */\n  issuedOn?: string;\n  /** Status reason description */\n  statusReason?: string;\n  /** Share capital in BRL */\n  shareCapital?: number;\n  /** Economic activities (CNAE) */\n  economicActivities?: LegalEntityEconomicActivity[];\n  /** Legal nature */\n  legalNature?: LegalEntityNature;\n  /** Partners and administrators */\n  partners?: LegalEntityPartner[];\n  /** Registration unit (city/office) */\n  registrationUnit?: string;\n  /** Organizational unit (headquarters/subsidiary) */\n  unit?: LegalEntityUnit;\n}\n\n/** State tax information from state tax info lookup */\nexport interface LegalEntityStateTaxInfo {\n  /** Trade name */\n  tradeName?: string;\n  /** Legal name */\n  name?: string;\n  /** Federal tax number (CNPJ) — numeric */\n  federalTaxNumber?: number;\n  /** Query date */\n  createdOn?: string;\n  /** Tax regime (CRT) */\n  taxRegime?: LegalEntityTaxRegime;\n  /** Legal nature code */\n  legalNature?: LegalEntityNatureCode;\n  /** Fiscal unit */\n  fiscalUnit?: string;\n  /** Registration unit */\n  createdUnit?: string;\n  /** Verification code */\n  checkCode?: string;\n  /** State tax registrations (Inscrições Estaduais) */\n  stateTaxes?: LegalEntityStateTax[];\n}\n\n/** State tax information for invoice evaluation */\nexport interface LegalEntityStateTaxForInvoiceInfo {\n  /** Trade name */\n  tradeName?: string;\n  /** Legal name */\n  name?: string;\n  /** Federal tax number (CNPJ) — numeric */\n  federalTaxNumber?: number;\n  /** Query date */\n  createdOn?: string;\n  /** Tax regime (CRT) */\n  taxRegime?: LegalEntityTaxRegime;\n  /** Legal nature code */\n  legalNature?: LegalEntityNatureCode;\n  /** Fiscal unit */\n  fiscalUnit?: string;\n  /** Registration unit */\n  createdUnit?: string;\n  /** Verification code */\n  checkCode?: string;\n  /** State tax registrations for invoice evaluation (extended status) */\n  stateTaxes?: LegalEntityStateTaxForInvoice[];\n}\n\n// ============================================================================\n// Natural Person Lookup Types (consulta-cpf)\n// ============================================================================\n\n/**\n * Known cadastral status values for CPF (situação cadastral na Receita Federal).\n * The union includes a `(string & {})` fallback to allow unknown future values\n * while still providing autocomplete for known statuses.\n */\nexport type NaturalPersonStatus =\n  | 'Regular'\n  | 'Suspensa'\n  | 'Cancelada'\n  | 'Titular Falecido'\n  | 'Pendente de Regularização'\n  | 'Nula'\n  | (string & {});\n\n/**\n * Response from the CPF cadastral status lookup endpoint.\n *\n * Returned by `GET /v1/naturalperson/status/{federalTaxNumber}/{birthDate}`\n * on `naturalperson.api.nfe.io`.\n */\nexport interface NaturalPersonStatusResponse {\n  /** Full name of the person */\n  name?: string;\n  /** CPF number (digits only) */\n  federalTaxNumber: string;\n  /** Date of birth (ISO 8601 date-time string) */\n  birthOn?: string;\n  /** Cadastral status at Receita Federal */\n  status?: NaturalPersonStatus;\n  /** Timestamp of when the query was created (ISO 8601 date-time string) */\n  createdOn?: string;\n}\n\n// ============================================================================\n// Tax Calculation Types (calculo-impostos-v1)\n// ============================================================================\n\n// --- Enums ---\n\n/**\n * Type of tax operation (incoming vs outgoing).\n *\n * - `'Outgoing'` — Saída (sale, shipment)\n * - `'Incoming'` — Entrada (purchase, receipt)\n */\nexport type TaxOperationType = 'Outgoing' | 'Incoming';\n\n/**\n * Origin of the merchandise for ICMS purposes.\n *\n * Mirrors the SEFAZ origin codes (0-8).\n */\nexport type TaxOrigin =\n  | 'National'\n  | 'ForeignDirectImport'\n  | 'ForeignInternalMarket'\n  | 'NationalWith40To70Import'\n  | 'NationalPpb'\n  | 'NationalWithLess40Import'\n  | 'ForeignDirectImportWithoutNationalSimilar'\n  | 'ForeignInternalMarketWithoutNationalSimilar'\n  | 'NationalWithGreater70Import';\n\n/**\n * Tax regime used in the Tax Calculation Engine.\n *\n * **Note:** This differs from the service-invoice {@link TaxRegime} which uses\n * Portuguese-language values. This enum uses the PascalCase values from the\n * calculo-impostos API.\n */\nexport type TaxCalcTaxRegime =\n  | 'NationalSimple'\n  | 'RealProfit'\n  | 'PresumedProfit'\n  | 'NationalSimpleSublimitExceeded'\n  | 'IndividualMicroEnterprise'\n  | 'Exempt';\n\n// --- Tax Component Interfaces ---\n\n/**\n * ICMS tax component — covers ICMS, ICMS-ST, FCP, and related calculations.\n *\n * All numeric fields are represented as strings matching the API's format.\n */\nexport interface TaxIcms {\n  /** Origem da mercadoria */\n  orig?: string;\n  /** Tributação do ICMS (CST) */\n  cst?: string;\n  /** Código de Situação da Operação – Simples Nacional (CSOSN) */\n  csosn?: string;\n  /** Modalidade de determinação da BC do ICMS */\n  modBC?: string;\n  /** Valor da BC do ICMS */\n  vBC?: string;\n  /** Percentual da Redução de BC */\n  pRedBC?: string;\n  /** Código do benefício fiscal relacionado a redução de base */\n  cBenefRBC?: string;\n  /** Alíquota do imposto */\n  pICMS?: string;\n  /** Valor do ICMS */\n  vICMS?: string;\n  /** Valor do ICMS da Operação */\n  vICMSOp?: string;\n  /** Modalidade de determinação da BC do ICMS ST */\n  modBCST?: string;\n  /** Valor da BC do ICMS ST */\n  vBCST?: string;\n  /** Percentual da Redução de BC do ICMS ST */\n  pRedBCST?: string;\n  /** Alíquota do imposto do ICMS ST */\n  pICMSST?: string;\n  /** Valor do ICMS ST */\n  vICMSST?: string;\n  /** Percentual da margem de valor Adicionado do ICMS ST */\n  pMVAST?: string;\n  /** Alíquota suportada pelo Consumidor Final */\n  pST?: string;\n  /** Valor da BC do ICMS ST retido */\n  vBCSTRet?: string;\n  /** Valor do ICMS ST retido */\n  vICMSSTRet?: string;\n  /** Valor da Base de Cálculo do FCP */\n  vBCFCP?: string;\n  /** Percentual do ICMS relativo ao Fundo de Combate à Pobreza (FCP) */\n  pFCP?: string;\n  /** Valor do Fundo de Combate à Pobreza (FCP) */\n  vFCP?: string;\n  /** Valor da Base de Cálculo do FCP retido por Substituição Tributária */\n  vBCFCPST?: string;\n  /** Percentual do FCP retido por Substituição Tributária */\n  pFCPST?: string;\n  /** Valor do FCP retido por Substituição Tributária */\n  vFCPST?: string;\n  /** Valor da Base de Cálculo do FCP retido anteriormente */\n  vBCFCPSTRet?: string;\n  /** Percentual do FCP retido anteriormente por Substituição Tributária */\n  pFCPSTRet?: string;\n  /** Valor do FCP retido por Substituição Tributária (retained) */\n  vFCPSTRet?: string;\n  /** Valor da base de cálculo efetiva */\n  vBCEfet?: string;\n  /** Percentual de redução da base de cálculo efetiva */\n  pRedBCEfet?: string;\n  /** Alíquota do ICMS efetiva */\n  pICMSEfet?: string;\n  /** Valor do ICMS efetivo */\n  vICMSEfet?: string;\n  /** Percentual do diferimento */\n  pDif?: string;\n  /** Valor do ICMS diferido */\n  vICMSDif?: string;\n  /** Valor do ICMS próprio do Substituto */\n  vICMSSubstituto?: string;\n  /** Alíquota aplicável de cálculo do crédito (Simples Nacional) */\n  pCredSN?: string;\n  /** Valor crédito do ICMS (Simples Nacional, LC 123 art. 23) */\n  vCredICMSSN?: string;\n  /** Percentual do diferimento do FCP */\n  pFCPDif?: string;\n  /** Valor do FCP diferido */\n  vFCPDif?: string;\n  /** Valor efetivo do FCP */\n  vFCPEfet?: string;\n  /** Valor do ICMS desonerado */\n  vICMSDeson?: string;\n  /** Motivo da desoneração do ICMS */\n  motDesICMS?: string;\n  /** Valor do ICMS-ST desonerado */\n  vICMSSTDeson?: string;\n  /** Motivo da desoneração do ICMS-ST */\n  motDesICMSST?: string;\n  /** Indica se o valor do ICMS desonerado deduz do valor do item */\n  indDeduzDeson?: string;\n}\n\n/**\n * ICMS interestadual (DIFAL / UF Destination) tax component.\n */\nexport interface TaxIcmsUfDest {\n  /** Valor da BC do ICMS na UF de destino */\n  vBCUFDest?: string;\n  /** Valor da BC FCP na UF de destino */\n  vBCFCPUFDest?: string;\n  /** Percentual do FCP na UF de destino */\n  pFCPUFDest?: string;\n  /** Alíquota interna da UF de destino */\n  pICMSUFDest?: string;\n  /** Alíquota interestadual das UF envolvidas */\n  pICMSInter?: string;\n  /** Percentual provisório de partilha do ICMS Interestadual */\n  pICMSInterPart?: string;\n  /** Valor do FCP na UF de destino */\n  vFCPUFDest?: string;\n  /** Valor do ICMS Interestadual para a UF de destino */\n  vICMSUFDest?: string;\n  /** Valor do ICMS Interestadual para a UF do remetente */\n  vICMSUFRemet?: string;\n}\n\n/**\n * PIS tax component.\n */\nexport interface TaxPis {\n  /** Código de Situação Tributária do PIS */\n  cst?: string;\n  /** Valor da Base de Cálculo do PIS */\n  vBC?: string;\n  /** Alíquota do PIS (em percentual) */\n  pPIS?: string;\n  /** Valor do PIS */\n  vPIS?: string;\n  /** Quantidade Vendida */\n  qBCProd?: string;\n  /** Alíquota do PIS (em reais) */\n  vAliqProd?: string;\n}\n\n/**\n * COFINS tax component.\n */\nexport interface TaxCofins {\n  /** Código de Situação Tributária da COFINS */\n  cst?: string;\n  /** Valor da Base de Cálculo do COFINS */\n  vBC?: string;\n  /** Alíquota do COFINS (em percentual) */\n  pCOFINS?: string;\n  /** Valor do COFINS */\n  vCOFINS?: string;\n  /** Quantidade Vendida */\n  qBCProd?: string;\n  /** Alíquota do COFINS (em reais) */\n  vAliqProd?: string;\n}\n\n/**\n * IPI tax component.\n */\nexport interface TaxIpi {\n  /** Código de Enquadramento Legal do IPI */\n  cEnq?: string;\n  /** Código da situação tributária do IPI */\n  cst?: string;\n  /** Valor da BC do IPI */\n  vBC?: string;\n  /** Alíquota do IPI */\n  pIPI?: string;\n  /** Quantidade total na unidade padrão para tributação */\n  qUnid?: string;\n  /** Valor por Unidade Tributável */\n  vUnid?: string;\n  /** Valor do IPI */\n  vIPI?: string;\n}\n\n/**\n * Import Tax (II) component.\n */\nexport interface TaxIi {\n  /** Valor BC do Imposto de Importação */\n  vBC?: string;\n  /** Valor despesas aduaneiras */\n  vDespAdu?: string;\n  /** Valor Imposto de Importação */\n  vII?: string;\n  /** Valor Imposto sobre Operações Financeiras */\n  vIOF?: string;\n  /** Valor dos encargos cambiais */\n  vEncCamb?: string;\n  /** Alíquota do Simples Nacional aplicável */\n  pCredSN?: string;\n  /** Valor crédito do ICMS (Simples Nacional) */\n  vCredICMSSN?: string;\n  /** Ativação do cálculo do custo de aquisição (0=Inativo, 1=Ativo) */\n  infCustoAquis?: string;\n}\n\n// --- Request Interfaces ---\n\n/**\n * Issuer data for the tax calculation request.\n */\nexport interface CalculateRequestIssuer {\n  /** Tax regime of the issuer */\n  taxRegime: TaxCalcTaxRegime;\n  /** Default tax profile for the issuer */\n  taxProfile?: string;\n  /** State of the issuer */\n  state: BrazilianState;\n}\n\n/**\n * Recipient data for the tax calculation request.\n */\nexport interface CalculateRequestRecipient {\n  /** Tax regime of the recipient (optional) */\n  taxRegime?: TaxCalcTaxRegime;\n  /** Default tax profile for the recipient */\n  taxProfile?: string;\n  /** State of the recipient */\n  state: BrazilianState;\n}\n\n/**\n * A single item (product) in the tax calculation request.\n */\nexport interface CalculateItemRequest {\n  /** Unique item identifier */\n  id: string;\n  /** Internal code for operation nature determination (1–9999) */\n  operationCode: number;\n  /** Acquisition purpose code */\n  acquisitionPurpose?: string;\n  /** Issuer tax profile for this specific item */\n  issuerTaxProfile?: string;\n  /** Recipient tax profile for this specific item */\n  recipientTaxProfile?: string;\n  /** Product SKU */\n  sku?: string;\n  /** NCM code (Nomenclatura Comum do Mercosul, up to 8 digits) */\n  ncm?: string;\n  /** CEST code (Código Especificador da Substituição Tributária, 7 digits) */\n  cest?: string;\n  /** Fiscal benefit code */\n  benefit?: string;\n  /** EX TIPI code (1–3 chars) */\n  exTipi?: string;\n  /** Origin of the merchandise */\n  origin: TaxOrigin;\n  /** Global Trade Item Number */\n  gtin?: string;\n  /** Taxable quantity */\n  quantity: number;\n  /** Taxable unit amount */\n  unitAmount: number;\n  /** Freight amount */\n  freightAmount?: number;\n  /** Insurance amount */\n  insuranceAmount?: number;\n  /** Discount amount */\n  discountAmount?: number;\n  /** Other accessory expenses */\n  othersAmount?: number;\n  /** ICMS input overrides (for import tax scenarios) */\n  icms?: TaxIcms;\n  /** Import tax input overrides */\n  ii?: TaxIi;\n}\n\n/**\n * Tax calculation request payload.\n *\n * Submit to `POST /tax-rules/{tenantId}/engine/calculate` to compute all\n * applicable Brazilian taxes (ICMS, ICMS-ST, PIS, COFINS, IPI, II) for\n * the given operation context and product items.\n *\n * @example\n * ```typescript\n * const request: CalculateRequest = {\n *   operationType: 'Outgoing',\n *   issuer: { state: 'SP', taxRegime: 'RealProfit' },\n *   recipient: { state: 'RJ' },\n *   items: [{\n *     id: '1',\n *     operationCode: 121,\n *     origin: 'National',\n *     quantity: 10,\n *     unitAmount: 100.00,\n *     ncm: '61091000'\n *   }]\n * };\n * ```\n */\nexport interface CalculateRequest {\n  /** Product collection identifier */\n  collectionId?: string;\n  /** Issuer (seller/shipper) fiscal data */\n  issuer: CalculateRequestIssuer;\n  /** Recipient (buyer/receiver) fiscal data */\n  recipient: CalculateRequestRecipient;\n  /** Type of operation */\n  operationType: TaxOperationType;\n  /** List of products/items to calculate taxes for */\n  items: CalculateItemRequest[];\n  /** Whether this is a product registration request (vs invoice issuance) */\n  isProductRegistration?: boolean;\n}\n\n// --- Response Interfaces ---\n\n/**\n * A single item in the tax calculation response with full tax breakdown.\n */\nexport interface CalculateItemResponse {\n  /** Item identifier (matches the request item id) */\n  id?: string;\n  /** CFOP — Código Fiscal de Operações e Prestações */\n  cfop?: number;\n  /** CEST code */\n  cest?: string;\n  /** Fiscal benefit code */\n  benefit?: string;\n  /** ICMS tax breakdown */\n  icms?: TaxIcms;\n  /** ICMS interestadual (DIFAL / UF destination) breakdown */\n  icmsUfDest?: TaxIcmsUfDest;\n  /** PIS tax breakdown */\n  pis?: TaxPis;\n  /** COFINS tax breakdown */\n  cofins?: TaxCofins;\n  /** IPI tax breakdown */\n  ipi?: TaxIpi;\n  /** Import tax (II) breakdown */\n  ii?: TaxIi;\n  /** Additional product information */\n  additionalInformation?: string;\n  /** Timestamp of the last rule modification (ISO 8601) */\n  lastModified?: string;\n  /** Registered product ID */\n  productId?: string;\n}\n\n/**\n * Tax calculation response containing per-item tax breakdowns.\n */\nexport interface CalculateResponse {\n  /** Calculated items with full tax data */\n  items?: CalculateItemResponse[];\n}\n\n// --- Tax Codes Types ---\n\n/**\n * A single tax code entry (operation code, acquisition purpose, or tax profile).\n */\nexport interface TaxCode {\n  /** The code identifier */\n  code?: string;\n  /** Human-readable description */\n  description?: string;\n}\n\n/**\n * Paginated response for tax code listings.\n */\nexport interface TaxCodePaginatedResponse {\n  /** List of tax code entries */\n  items?: TaxCode[];\n  /** Current page number (1-based) */\n  currentPage?: number;\n  /** Total number of pages */\n  totalPages?: number;\n  /** Total count of entries */\n  totalCount?: number;\n}\n\n/**\n * Options for listing tax codes (pagination).\n *\n * Uses the API's native pagination model (`pageIndex`/`pageCount`),\n * which differs from the OData-style `$skip`/`$top` used by other resources.\n */\nexport interface TaxCodeListOptions {\n  /** Page index (1-based, default: 1) */\n  pageIndex?: number;\n  /** Number of items per page (default: 50) */\n  pageCount?: number;\n}\n\n// ============================================================================\n// Product Invoice (NF-e Issuance) Types — nf-produto-v2\n// ============================================================================\n\n// Enum types (string literal unions)\n// ----------------------------------------------------------------------------\n\n/** Environment type for NF-e product invoice operations */\nexport type NfeEnvironmentType = 'None' | 'Production' | 'Test';\n\n/** Status of a product invoice (NF-e) in the issuance lifecycle */\nexport type NfeInvoiceStatus =\n  | 'None'\n  | 'Created'\n  | 'Processing'\n  | 'Issued'\n  | 'IssuedContingency'\n  | 'Cancelled'\n  | 'Disabled'\n  | 'IssueDenied'\n  | 'Error';\n\n/** Brazilian state code (UF) */\nexport type NfeStateCode =\n  | 'NA' | 'RO' | 'AC' | 'AM' | 'RR' | 'PA' | 'AP' | 'TO'\n  | 'MA' | 'PI' | 'CE' | 'RN' | 'PB' | 'PE' | 'AL' | 'SE' | 'BA'\n  | 'MG' | 'ES' | 'RJ' | 'SP' | 'PR' | 'SC' | 'RS'\n  | 'MS' | 'MT' | 'GO' | 'DF' | 'EX';\n\n/** Operation type (incoming/outgoing) for NF-e */\nexport type NfeOperationType = 'Outgoing' | 'Incoming';\n\n/** Purpose of the NF-e invoice */\nexport type NfePurposeType = 'None' | 'Normal' | 'Complement' | 'Adjustment' | 'Devolution';\n\n/** Payment method for NF-e */\nexport type NfePaymentMethod =\n  | 'Cash' | 'Cheque' | 'CreditCard' | 'DebitCard'\n  | 'StoreCredict' | 'FoodVouchers' | 'MealVouchers' | 'GiftVouchers'\n  | 'FuelVouchers' | 'BankBill' | 'BankDeposit' | 'InstantPayment'\n  | 'WireTransfer' | 'Cashback' | 'WithoutPayment' | 'Others';\n\n/** Shipping modality for NF-e transport */\nexport type NfeShippingModality =\n  | 'ByIssuer' | 'ByReceiver' | 'ByThirdParties'\n  | 'OwnBySender' | 'OwnByBuyer' | 'Free';\n\n/** Consumer presence indicator for NF-e */\nexport type NfeConsumerPresenceType =\n  | 'None' | 'Presence' | 'Internet' | 'Telephone'\n  | 'Delivery' | 'OthersNonPresenceOperation';\n\n/** DANFE print format */\nexport type NfePrintType =\n  | 'None' | 'NFeNormalPortrait' | 'NFeNormalLandscape'\n  | 'NFeSimplified' | 'DANFE_NFC_E' | 'DANFE_NFC_E_MSG_ELETRONICA';\n\n/** Person type */\nexport type NfePersonType = 'Undefined' | 'NaturalPerson' | 'LegalEntity' | 'Company' | 'Customer';\n\n/** Destination of the operation */\nexport type NfeDestination =\n  | 'None' | 'Internal_Operation' | 'Interstate_Operation' | 'International_Operation';\n\n/** Consumer type indicator */\nexport type NfeConsumerType = 'FinalConsumer' | 'Normal';\n\n/** Payment type (cash or term) */\nexport type NfePaymentType = 'InCash' | 'Term';\n\n/** Receiver state tax indicator */\nexport type NfeReceiverStateTaxIndicator = 'None' | 'TaxPayer' | 'Exempt' | 'NonTaxPayer';\n\n/** Card flag/brand for payment */\nexport type NfeFlagCard =\n  | 'None' | 'Visa' | 'Mastercard' | 'AmericanExpress' | 'Sorocred'\n  | 'DinersClub' | 'Elo' | 'Hipercard' | 'Aura' | 'Cabal' | 'Alelo'\n  | 'BanesCard' | 'CalCard' | 'Credz' | 'Discover' | 'GoodCard'\n  | 'GreenCard' | 'Hiper' | 'JCB' | 'Mais' | 'MaxVan' | 'Policard'\n  | 'RedeCompras' | 'Sodexo' | 'ValeCard' | 'Verocheque' | 'VR'\n  | 'Ticket' | 'Other';\n\n/** Integration payment type */\nexport type NfeIntegrationPaymentType = 'Integrated' | 'NotIntegrated';\n\n/** Intermediation type */\nexport type NfeIntermediationType = 'None' | 'ByOwn' | 'ImportOnBehalf' | 'ByOrder';\n\n/** Tax regime */\nexport type NfeTaxRegime =\n  | 'None' | 'LucroReal' | 'LucroPresumido' | 'SimplesNacional'\n  | 'SimplesNacionalExcessoSublimite' | 'MicroempreendedorIndividual' | 'Isento';\n\n/** Special tax regime */\nexport type NfeSpecialTaxRegime =\n  | 'Nenhum' | 'MicroempresaMunicipal' | 'Estimativa'\n  | 'SociedadeDeProfissionais' | 'Cooperativa' | 'MicroempreendedorIndividual'\n  | 'MicroempresarioEmpresaPequenoPorte' | 'Automatico';\n\n/** State tax processing authorizer */\nexport type NfeStateTaxProcessingAuthorizer = 'Normal' | 'EPEC';\n\n/** Flow status for file operations */\nexport type NfeFlowStatus = string;\n\n// Request/Response types — Product Invoices\n// ----------------------------------------------------------------------------\n\n/** Address in NF-e context */\nexport interface NfeAddress {\n  /** Street name */\n  street?: string;\n  /** Street number */\n  number?: string;\n  /** Additional info (complement) */\n  district?: string;\n  /** City */\n  city?: NfeCity;\n  /** State code */\n  state?: NfeStateCode;\n  /** Postal code (CEP) */\n  postalCode?: string;\n  /** Country code */\n  countryCode?: string;\n  /** Country name */\n  country?: string;\n  /** Additional info */\n  additionalInformation?: string;\n  [key: string]: unknown;\n}\n\n/** City reference */\nexport interface NfeCity {\n  /** IBGE city code */\n  code?: string;\n  /** City name */\n  name?: string;\n}\n\n/** Buyer/recipient information for NF-e */\nexport interface NfeProductInvoiceBuyer {\n  /** Buyer name */\n  name?: string;\n  /** CNPJ or CPF (numeric) */\n  federalTaxNumber?: number;\n  /** Email */\n  email?: string;\n  /** Buyer address */\n  address?: NfeAddress;\n  /** Person type */\n  type?: NfePersonType;\n  /** State tax number (IE) */\n  stateTaxNumber?: string;\n  /** State tax indicator */\n  stateTaxNumberIndicator?: NfeReceiverStateTaxIndicator;\n  /** Trade name */\n  tradeName?: string;\n  /** ISUF (SUFRAMA registration) */\n  isuf?: string;\n  [key: string]: unknown;\n}\n\n/** Card payment details */\nexport interface NfeCardResource {\n  /** Card flag/brand */\n  flagCard?: NfeFlagCard;\n  /** Integration type */\n  integrationType?: NfeIntegrationPaymentType;\n  /** Authorization number */\n  authorizationNumber?: string;\n  /** Card number */\n  cardNumber?: string;\n  [key: string]: unknown;\n}\n\n/** Payment detail entry */\nexport interface NfePaymentDetail {\n  /** Payment method */\n  method?: NfePaymentMethod;\n  /** Payment method description */\n  methodDescription?: string;\n  /** Payment type (cash/term) */\n  paymentType?: NfePaymentType;\n  /** Payment amount */\n  amount?: number;\n  /** Card information */\n  card?: NfeCardResource;\n  /** Payment date */\n  paymentDate?: string;\n  /** CNPJ transacional do pagamento */\n  federalTaxNumberPag?: string;\n  /** UF do CNPJ do pagamento */\n  statePag?: string;\n  [key: string]: unknown;\n}\n\n/** Payment group with details and change */\nexport interface NfePaymentResource {\n  /** Payment details */\n  paymentDetail?: NfePaymentDetail[];\n  /** Change amount (troco) */\n  payBack?: number;\n}\n\n/** Billing information (cobrança) */\nexport interface NfeBillingResource {\n  /** Invoice reference */\n  invoice?: NfeBillingInvoice;\n  /** Duplicates (parcelas) */\n  duplicates?: NfeDuplicateResource[];\n}\n\n/** Billing invoice reference */\nexport interface NfeBillingInvoice {\n  /** Invoice number */\n  number?: string;\n  /** Original amount */\n  originalAmount?: number;\n  /** Discount amount */\n  discountAmount?: number;\n  /** Net amount */\n  netAmount?: number;\n  [key: string]: unknown;\n}\n\n/** Billing duplicate (parcela) */\nexport interface NfeDuplicateResource {\n  /** Duplicate number */\n  number?: string;\n  /** Expiration date */\n  expirationOn?: string;\n  /** Amount */\n  amount?: number;\n}\n\n/** ICMS tax information for an item */\nexport interface NfeIcmsTaxResource {\n  /** Origin of goods */\n  origin?: string;\n  /** CST (Código de Situação Tributária) */\n  cst?: string;\n  /** CSOSN (Código de Situação da Operação – Simples Nacional) */\n  csosn?: string;\n  /** Tax base amount */\n  baseTax?: number;\n  /** Tax rate (%) */\n  rate?: number;\n  /** Tax amount */\n  amount?: number;\n  /** Modality of ICMS base calculation */\n  modality?: number;\n  /** ICMS ST base amount */\n  baseTaxST?: number;\n  /** ICMS ST rate */\n  rateST?: number;\n  /** ICMS ST amount */\n  amountST?: number;\n  [key: string]: unknown;\n}\n\n/** IPI tax information */\nexport interface NfeIpiTaxResource {\n  /** CST */\n  cst?: string;\n  /** Tax base */\n  baseTax?: number;\n  /** Rate */\n  rate?: number;\n  /** Amount */\n  amount?: number;\n  /** IPI enquadramento code */\n  ipiCode?: string;\n  [key: string]: unknown;\n}\n\n/** PIS tax information */\nexport interface NfePisTaxResource {\n  /** CST */\n  cst?: string;\n  /** Tax base */\n  baseTax?: number;\n  /** Rate */\n  rate?: number;\n  /** Amount */\n  amount?: number;\n  /** Product quantity base */\n  baseTaxProductQuantity?: number;\n  /** Product rate (in reais) */\n  productRate?: number;\n}\n\n/** COFINS tax information */\nexport interface NfeCofinsTaxResource {\n  /** CST */\n  cst?: string;\n  /** Tax base */\n  baseTax?: number;\n  /** Rate */\n  rate?: number;\n  /** Amount */\n  amount?: number;\n  /** Product quantity base */\n  baseTaxProductQuantity?: number;\n  /** Product rate (in reais) */\n  productRate?: number;\n}\n\n/** II (Import tax) information */\nexport interface NfeIiTaxResource {\n  /** Tax base */\n  baseTax?: number;\n  /** Custom expenses */\n  customExpenses?: number;\n  /** IOF amount */\n  iofAmount?: number;\n  /** II amount */\n  amount?: number;\n}\n\n/** ICMS UF Destination tax (partilha) */\nexport interface NfeIcmsUfDestinationTaxResource {\n  /** Base tax amount */\n  baseTax?: number;\n  /** FCP rate */\n  fcpRate?: number;\n  /** Rate */\n  rate?: number;\n  /** Interestadual rate */\n  interestadualRate?: number;\n  /** Provisorio rate */\n  provisorioRate?: number;\n  /** FCP amount */\n  fcpAmount?: number;\n  /** Destination amount */\n  destinationAmount?: number;\n  /** Origin amount */\n  originAmount?: number;\n  [key: string]: unknown;\n}\n\n/** Tax information for an invoice item */\nexport interface NfeInvoiceItemTax {\n  /** Total approximate tax value */\n  totalTax?: number;\n  /** ICMS tax */\n  icms?: NfeIcmsTaxResource;\n  /** IPI tax */\n  ipi?: NfeIpiTaxResource;\n  /** II (import) tax */\n  ii?: NfeIiTaxResource;\n  /** PIS tax */\n  pis?: NfePisTaxResource;\n  /** COFINS tax */\n  cofins?: NfeCofinsTaxResource;\n  /** ICMS UF destination */\n  icmsDestination?: NfeIcmsUfDestinationTaxResource;\n}\n\n/** Tax determination resource for automatic tax calculation */\nexport interface NfeTaxDeterminationResource {\n  /** Operation code for tax determination */\n  operationCode?: number;\n  /** Issuer tax profile */\n  issuerTaxProfile?: string;\n  /** Buyer tax profile */\n  buyerTaxProfile?: string;\n  /** Origin */\n  origin?: string;\n  /** Acquisition purpose */\n  acquisitionPurpose?: string;\n}\n\n/** Invoice item (product/service detail) */\nexport interface NfeInvoiceItemResource {\n  /** Product/service code */\n  code?: string;\n  /** GTIN barcode */\n  codeGTIN?: string;\n  /** Product/service description */\n  description?: string;\n  /** NCM code */\n  ncm?: string;\n  /** NVE codes */\n  nve?: string[];\n  /** EXTIPI code */\n  extipi?: string;\n  /** CFOP code */\n  cfop?: number;\n  /** Commercial unit */\n  unit?: string;\n  /** Commercial quantity */\n  quantity?: number;\n  /** Unit amount */\n  unitAmount?: number;\n  /** Total amount */\n  totalAmount?: number;\n  /** Tax GTIN */\n  codeTaxGTIN?: string;\n  /** Tax unit */\n  unitTax?: string;\n  /** Tax quantity */\n  quantityTax?: number;\n  /** Tax unit amount */\n  taxUnitAmount?: number;\n  /** Freight amount */\n  freightAmount?: number;\n  /** Insurance amount */\n  insuranceAmount?: number;\n  /** Discount amount */\n  discountAmount?: number;\n  /** Other expenses */\n  othersAmount?: number;\n  /** Indicates if value enters total */\n  totalIndicator?: boolean;\n  /** CEST code */\n  cest?: string;\n  /** Tax details */\n  tax?: NfeInvoiceItemTax;\n  /** Additional product information */\n  additionalInformation?: string;\n  /** Purchase order number */\n  numberOrderBuy?: string;\n  /** Purchase order item number */\n  itemNumberOrderBuy?: number;\n  /** FCI number */\n  importControlSheetNumber?: string;\n  /** Fuel details */\n  fuelDetail?: Record<string, unknown>;\n  /** Benefit code */\n  benefit?: string;\n  /** Import declarations */\n  importDeclarations?: Record<string, unknown>[];\n  /** Export details */\n  exportDetails?: Record<string, unknown>[];\n  /** Tax determination */\n  taxDetermination?: NfeTaxDeterminationResource;\n  [key: string]: unknown;\n}\n\n/** Transport information for NF-e */\nexport interface NfeTransportInformation {\n  /** Shipping modality */\n  shippingModality?: NfeShippingModality;\n  /** Transport group (carrier info) */\n  transportGroup?: NfeTransportGroupResource;\n  /** Volumes */\n  volumes?: NfeVolumeResource[];\n  [key: string]: unknown;\n}\n\n/** Transport group/carrier resource */\nexport interface NfeTransportGroupResource {\n  /** Carrier name */\n  name?: string;\n  /** CNPJ or CPF */\n  federalTaxNumber?: string;\n  /** State tax number (IE) */\n  stateTaxNumber?: string;\n  /** Address (full) */\n  address?: string;\n  /** City name */\n  city?: string;\n  /** State code */\n  state?: string;\n  /** Vehicle plate */\n  vehiclePlate?: string;\n  /** Vehicle UF */\n  vehicleUf?: string;\n  /** Vehicle RNTC */\n  vehicleRntc?: string;\n  [key: string]: unknown;\n}\n\n/** Volume resource for transport */\nexport interface NfeVolumeResource {\n  /** Quantity */\n  quantity?: number;\n  /** Species */\n  species?: string;\n  /** Brand */\n  brand?: string;\n  /** Numbering */\n  numbering?: string;\n  /** Net weight */\n  netWeight?: number;\n  /** Gross weight */\n  grossWeight?: number;\n  /** Seal numbers */\n  seals?: string[];\n  [key: string]: unknown;\n}\n\n/** Additional information for the invoice */\nexport interface NfeAdditionalInformation {\n  /** Additional info for tax authority (infAdFisco) */\n  taxAdministration?: string;\n  /** Complementary info for taxpayer (infCpl) */\n  taxpayer?: string;\n  /** Referenced processes */\n  referencedProcess?: Record<string, unknown>[];\n  [key: string]: unknown;\n}\n\n/** Export hint and details */\nexport interface NfeExportResource {\n  /** State that generated the invoice */\n  exportState?: NfeStateCode;\n  /** Export location municipio */\n  exportLocation?: string;\n  /** Export hint details */\n  hint?: Record<string, unknown>;\n  [key: string]: unknown;\n}\n\n/** Issuer from request (issuer overrides) */\nexport interface NfeIssuerFromRequest {\n  /** IE do Substituto Tributário (IEST) */\n  stStateTaxNumber?: string;\n}\n\n/** Transaction intermediate resource */\nexport interface NfeIntermediateResource {\n  /** CNPJ of intermediary */\n  federalTaxNumber?: number;\n  /** Identifier at intermediary */\n  identifier?: string;\n}\n\n/** Delivery information */\nexport interface NfeDeliveryInformation {\n  /** Account ID */\n  accountId?: string;\n  /** Entity ID */\n  id?: string;\n  /** Name */\n  name?: string;\n  /** CNPJ or CPF */\n  federalTaxNumber?: number;\n  /** Email */\n  email?: string;\n  /** Address */\n  address?: NfeAddress;\n  /** Person type */\n  type?: NfePersonType;\n  /** State tax number */\n  stateTaxNumber?: string;\n  [key: string]: unknown;\n}\n\n/** Withdrawal information */\nexport interface NfeWithdrawalInformation {\n  /** Account ID */\n  accountId?: string;\n  /** Entity ID */\n  id?: string;\n  /** Name */\n  name?: string;\n  /** CNPJ or CPF */\n  federalTaxNumber?: number;\n  /** Email */\n  email?: string;\n  /** Address */\n  address?: NfeAddress;\n  /** Person type */\n  type?: NfePersonType;\n  /** State tax number */\n  stateTaxNumber?: string;\n  [key: string]: unknown;\n}\n\n/** Totals (request — partial totals sent on issue) */\nexport interface NfeTotals {\n  /** ICMS total */\n  icms?: Record<string, unknown>;\n  /** ISSQN total */\n  issqn?: Record<string, unknown>;\n  [key: string]: unknown;\n}\n\n/** Total resource (response — full totals from API) */\nexport interface NfeTotalResource {\n  /** ICMS total */\n  icms?: Record<string, unknown>;\n  /** ISSQN total */\n  issqn?: Record<string, unknown>;\n  [key: string]: unknown;\n}\n\n/** Authorization details */\nexport interface NfeAuthorizationResource {\n  /** Protocol number */\n  protocol?: string;\n  /** Authorization date */\n  sentOn?: string;\n  /** Authorization status */\n  status?: string;\n  /** Access key (44 digits) */\n  accessKey?: string;\n  /** Reason */\n  reason?: string;\n  [key: string]: unknown;\n}\n\n/** Contingency details */\nexport interface NfeContingencyDetails {\n  /** Authorizer used */\n  authorizer?: NfeStateTaxProcessingAuthorizer;\n  /** Start time */\n  startedOn?: string;\n  /** Reason for contingency */\n  reason?: string;\n}\n\n/** Activity/event resource */\nexport interface NfeActivityResource {\n  /** Event type */\n  type?: string;\n  /** Event type description */\n  typeDescription?: string;\n  /** Sequence number */\n  sequence?: number;\n  /** Event creation date */\n  createdOn?: string;\n  /** Event data */\n  data?: Record<string, unknown>;\n  [key: string]: unknown;\n}\n\n/** Events base resource */\nexport interface NfeInvoiceEventsBase {\n  /** List of events */\n  events?: NfeActivityResource[];\n  /** Whether more events exist */\n  hasMore?: boolean;\n}\n\n/**\n * Data for issuing a product invoice (NF-e).\n * Corresponds to `ProductInvoiceQueueIssueResource` in the OpenAPI spec.\n */\nexport interface NfeProductInvoiceIssueData {\n  /** Invoice ID (optional, auto-generated) */\n  id?: string;\n  /** Invoice serie number */\n  serie?: number;\n  /** Invoice number */\n  number?: number;\n  /** Operation date/time (UTC ISO 8601) */\n  operationOn?: string;\n  /** Operation nature description (natOp) */\n  operationNature?: string;\n  /** Operation type */\n  operationType?: NfeOperationType;\n  /** Destination */\n  destination?: NfeDestination;\n  /** DANFE print type */\n  printType?: NfePrintType;\n  /** Purpose type */\n  purposeType?: NfePurposeType;\n  /** Consumer type */\n  consumerType?: NfeConsumerType;\n  /** Consumer presence type */\n  presenceType?: NfeConsumerPresenceType;\n  /** Contingency date/time */\n  contingencyOn?: string;\n  /** Contingency justification */\n  contingencyJustification?: string;\n  /** Buyer information */\n  buyer?: NfeProductInvoiceBuyer;\n  /** Transport information */\n  transport?: NfeTransportInformation;\n  /** Additional information */\n  additionalInformation?: NfeAdditionalInformation;\n  /** Export information */\n  export?: NfeExportResource;\n  /** Invoice items (products/services) */\n  items?: NfeInvoiceItemResource[];\n  /** Billing information */\n  billing?: NfeBillingResource;\n  /** Issuer overrides */\n  issuer?: NfeIssuerFromRequest;\n  /** Transaction intermediate */\n  transactionIntermediate?: NfeIntermediateResource;\n  /** Delivery information */\n  delivery?: NfeDeliveryInformation;\n  /** Withdrawal information */\n  withdrawal?: NfeWithdrawalInformation;\n  /** Payment groups */\n  payment?: NfePaymentResource[];\n  /** Totals */\n  totals?: NfeTotals;\n  [key: string]: unknown;\n}\n\n/** Issuer resource (in responses) */\nexport interface NfeIssuerResource {\n  /** Account ID */\n  accountId?: string;\n  /** Issuer entity ID */\n  id?: string;\n  /** Name or company name */\n  name?: string;\n  /** CNPJ or CPF */\n  federalTaxNumber?: number;\n  /** Email */\n  email?: string;\n  /** Address */\n  address?: NfeAddress;\n  /** Person type */\n  type?: NfePersonType;\n  /** Trade name */\n  tradeName?: string;\n  /** Opening date */\n  openningDate?: string;\n  /** Tax regime */\n  taxRegime?: NfeTaxRegime;\n  /** Special tax regime */\n  specialTaxRegime?: NfeSpecialTaxRegime;\n  /** Regional tax number (IE) */\n  regionalTaxNumber?: number;\n  /** Municipal tax number (IM) */\n  municipalTaxNumber?: string;\n  /** State tax number for ST */\n  stStateTaxNumber?: string;\n  [key: string]: unknown;\n}\n\n/**\n * Full product invoice (NF-e) response.\n * Corresponds to `InvoiceResource` in the OpenAPI spec.\n */\nexport interface NfeProductInvoice {\n  /** Invoice ID */\n  id?: string;\n  /** Serie number */\n  serie?: number;\n  /** Invoice number */\n  number?: number;\n  /** Invoice status */\n  status?: NfeInvoiceStatus;\n  /** Authorization details */\n  authorization?: NfeAuthorizationResource;\n  /** Contingency details */\n  contingencyDetails?: NfeContingencyDetails;\n  /** Operation nature */\n  operationNature?: string;\n  /** Creation date */\n  createdOn?: string;\n  /** Modification date */\n  modifiedOn?: string;\n  /** Operation date */\n  operationOn?: string;\n  /** Operation type */\n  operationType?: NfeOperationType;\n  /** Environment type */\n  environmentType?: NfeEnvironmentType;\n  /** Purpose type */\n  purposeType?: NfePurposeType;\n  /** Issuer */\n  issuer?: NfeIssuerResource;\n  /** Buyer */\n  buyer?: NfeProductInvoiceBuyer;\n  /** Totals */\n  totals?: NfeTotalResource;\n  /** Transport information */\n  transport?: NfeTransportInformation;\n  /** Additional information */\n  additionalInformation?: NfeAdditionalInformation;\n  /** Export information */\n  export?: NfeExportResource;\n  /** Billing */\n  billing?: NfeBillingResource;\n  /** Payment groups */\n  payment?: NfePaymentResource[];\n  /** Transaction intermediate */\n  transactionIntermediate?: NfeIntermediateResource;\n  /** Delivery information */\n  delivery?: NfeDeliveryInformation;\n  /** Withdrawal information */\n  withdrawal?: NfeWithdrawalInformation;\n  /** Last events */\n  lastEvents?: NfeInvoiceEventsBase;\n  [key: string]: unknown;\n}\n\n/** Product invoice without events (used in list responses) */\nexport interface NfeProductInvoiceWithoutEvents {\n  /** Invoice ID */\n  id?: string;\n  /** Serie number */\n  serie?: number;\n  /** Invoice number */\n  number?: number;\n  /** Invoice status */\n  status?: NfeInvoiceStatus;\n  /** Authorization details */\n  authorization?: NfeAuthorizationResource;\n  /** Contingency details */\n  contingencyDetails?: NfeContingencyDetails;\n  /** Operation nature */\n  operationNature?: string;\n  /** Creation date */\n  createdOn?: string;\n  /** Modification date */\n  modifiedOn?: string;\n  /** Operation date */\n  operationOn?: string;\n  /** Operation type */\n  operationType?: NfeOperationType;\n  /** Environment type */\n  environmentType?: NfeEnvironmentType;\n  /** Purpose type */\n  purposeType?: NfePurposeType;\n  /** Issuer */\n  issuer?: NfeIssuerResource;\n  /** Buyer */\n  buyer?: NfeProductInvoiceBuyer;\n  /** Totals */\n  totals?: NfeTotalResource;\n  /** Transport information */\n  transport?: NfeTransportInformation;\n  /** Additional information */\n  additionalInformation?: NfeAdditionalInformation;\n  /** Export information */\n  export?: NfeExportResource;\n  /** Billing */\n  billing?: NfeBillingResource;\n  /** Payment groups */\n  payment?: NfePaymentResource[];\n  /** Transaction intermediate */\n  transactionIntermediate?: NfeIntermediateResource;\n  /** Delivery information */\n  delivery?: NfeDeliveryInformation;\n  /** Withdrawal information */\n  withdrawal?: NfeWithdrawalInformation;\n  [key: string]: unknown;\n}\n\n/** Options for listing product invoices (cursor-based pagination) */\nexport interface NfeProductInvoiceListOptions {\n  /** Environment (required) */\n  environment: NfeEnvironmentType;\n  /** Cursor: start after this ID */\n  startingAfter?: string;\n  /** Cursor: end before this ID */\n  endingBefore?: string;\n  /** Number of results per page (default: 10) */\n  limit?: number;\n  /** ElasticSearch query string */\n  q?: string;\n}\n\n/** Paginated list of product invoices */\nexport interface NfeProductInvoiceListResponse {\n  /** List of invoices (without events) */\n  productInvoices?: NfeProductInvoiceWithoutEvents[];\n  /** Whether more results exist */\n  hasMore?: boolean;\n}\n\n/** Paginated list of invoice items */\nexport interface NfeInvoiceItemsResponse {\n  /** Account ID */\n  accountId?: string;\n  /** Company ID */\n  companyId?: string;\n  /** Invoice ID */\n  id?: string;\n  /** Invoice items */\n  items?: NfeInvoiceItemResource[];\n  /** Whether more items exist */\n  hasMore?: boolean;\n}\n\n/** Paginated list of invoice events */\nexport interface NfeProductInvoiceEventsResponse {\n  /** Invoice ID */\n  id?: string;\n  /** Account ID */\n  accountId?: string;\n  /** Company ID */\n  companyId?: string;\n  /** List of events */\n  events?: NfeActivityResource[];\n  /** Whether more events exist */\n  hasMore?: boolean;\n}\n\n/** Options for listing items/events (cursor pagination) */\nexport interface NfeProductInvoiceSubListOptions {\n  /** Number of results per page (default: 10) */\n  limit?: number;\n  /** Cursor: start after (default: 0) */\n  startingAfter?: number | string;\n}\n\n/** File resource (PDF/XML download response) — product and consumer invoices. */\nexport interface NfeFileResource {\n  /** Absolute URI to the file */\n  uri?: string;\n}\n\n/**\n * File resource returned by the INBOUND routes\n * (`/v2/companies/{id}/inbound/{accessKey}/xml` and `/pdf`, shared by CT-e and\n * NF-e distribution).\n *\n * Deliberately separate from {@link NfeFileResource}: the inbound routes name the\n * field `publicTemporaryUri`, not `uri`. Two envelopes, two types — verified live\n * on 2026-09-01, see `tests/fixtures/live-contracts/inbound-download.json`.\n *\n * The URI is a pre-signed, time-limited link. No binary is ever returned on these\n * routes, and the `Accept` header does not change the response.\n */\nexport interface InboundFileResource {\n  /** Pre-signed, time-limited URI to the document. Download is up to the caller. */\n  publicTemporaryUri?: string;\n}\n\n/** Request cancellation response */\nexport interface NfeRequestCancellationResource {\n  /** Account ID */\n  accountId?: string;\n  /** Company ID */\n  companyId?: string;\n  /** Product invoice ID */\n  productInvoiceId?: string;\n  /** Reason for cancellation */\n  reason?: string;\n}\n\n/** Disablement request data */\nexport interface NfeDisablementData {\n  /** Environment */\n  environment: NfeEnvironmentType;\n  /** Serie number */\n  serie: number;\n  /** State code */\n  state: NfeStateCode;\n  /** Beginning invoice number */\n  beginNumber: number;\n  /** Last invoice number (same as beginNumber for a single number) */\n  lastNumber: number;\n  /** Reason for disablement */\n  reason?: string;\n}\n\n/** Disablement response */\nexport interface NfeDisablementResource {\n  /** Environment */\n  environment?: NfeEnvironmentType;\n  /** Serie */\n  serie?: number;\n  /** State code */\n  state?: NfeStateCode;\n  /** Beginning number */\n  beginNumber?: number;\n  /** Last number */\n  lastNumber?: number;\n  /** Reason */\n  reason?: string;\n}\n\n// ============================================================================\n// State Tax (Inscrição Estadual) Types — nf-produto-v2\n// ============================================================================\n\n/** State tax type (emission type) */\nexport type NfeStateTaxType = 'default' | 'nFe' | 'nFCe';\n\n/** State tax environment type */\nexport type NfeStateTaxEnvironmentType = 'none' | 'production' | 'test';\n\n/** State tax status */\nexport type NfeStateTaxStatus = 'inactive' | 'none' | 'active';\n\n/** State tax state code (lowercase as in API) */\nexport type NfeStateTaxStateCode =\n  | 'rO' | 'aC' | 'aM' | 'rR' | 'pA' | 'aP' | 'tO'\n  | 'mA' | 'pI' | 'cE' | 'rN' | 'pB' | 'pE' | 'aL' | 'sE' | 'bA'\n  | 'mG' | 'eS' | 'rJ' | 'sP' | 'pR' | 'sC' | 'rS'\n  | 'mS' | 'mT' | 'gO' | 'dF' | 'eX' | 'nA';\n\n/** State tax special tax regime (lowercase as in API) */\nexport type NfeStateTaxSpecialTaxRegime =\n  | 'automatico' | 'nenhum' | 'microempresaMunicipal' | 'estimativa'\n  | 'sociedadeDeProfissionais' | 'cooperativa' | 'microempreendedorIndividual'\n  | 'microempresarioEmpresaPequenoPorte';\n\n/** Security credential for NFCe */\nexport interface NfeSecurityCredential {\n  /** Credential ID */\n  id?: number;\n  /** Security code */\n  code?: string;\n}\n\n/** Full state tax record (response) */\nexport interface NfeStateTax {\n  /** State tax ID */\n  id?: string;\n  /** Company ID */\n  companyId?: string;\n  /** Account ID */\n  accountId?: string;\n  /** State code */\n  code?: NfeStateTaxStateCode;\n  /** Environment type */\n  environmentType?: NfeStateTaxEnvironmentType;\n  /** State tax number (IE) */\n  taxNumber?: string;\n  /** Serie for emission */\n  serie?: number;\n  /** Number for emission */\n  number?: number;\n  /** Status */\n  status?: NfeStateTaxStatus;\n  /** Special tax regime */\n  specialTaxRegime?: NfeStateTaxSpecialTaxRegime;\n  /** Security credential (for NFCe) */\n  securityCredential?: NfeSecurityCredential;\n  /** Emission type */\n  type?: NfeStateTaxType;\n  /** All series for this state tax */\n  series?: number[];\n  /** Batch ID */\n  batchId?: number;\n  /** Creation date */\n  createdOn?: string;\n  /** Modification date */\n  modifiedOn?: string;\n}\n\n/** Data for creating a state tax registration */\nexport interface NfeStateTaxCreateData {\n  /** State tax number (IE) — required */\n  taxNumber: string;\n  /** Serie for emission — required */\n  serie: number;\n  /** Number for emission — required */\n  number: number;\n  /** State code */\n  code?: NfeStateTaxStateCode;\n  /** Environment type */\n  environmentType?: NfeStateTaxEnvironmentType;\n  /** Special tax regime */\n  specialTaxRegime?: NfeStateTaxSpecialTaxRegime;\n  /** Security credential (for NFCe) */\n  securityCredential?: NfeSecurityCredential;\n  /** Emission type */\n  type?: NfeStateTaxType;\n}\n\n/** Data for updating a state tax registration */\nexport interface NfeStateTaxUpdateData {\n  /** State tax number (IE) */\n  taxNumber?: string;\n  /** Serie for emission */\n  serie?: number;\n  /** Number for emission */\n  number?: number;\n  /** State code */\n  code?: NfeStateTaxStateCode;\n  /** Environment type */\n  environmentType?: NfeStateTaxEnvironmentType;\n  /** Special tax regime */\n  specialTaxRegime?: NfeStateTaxSpecialTaxRegime;\n  /** Security credential (for NFCe) */\n  securityCredential?: NfeSecurityCredential;\n  /** Emission type */\n  type?: NfeStateTaxType;\n}\n\n/** Paginated list of state tax registrations */\nexport interface NfeStateTaxListResponse {\n  /** List of state taxes */\n  stateTaxes?: NfeStateTax[];\n}\n\n/** Options for listing state taxes (cursor pagination) */\nexport interface NfeStateTaxListOptions {\n  /** Cursor: start after this ID */\n  startingAfter?: string;\n  /** Cursor: end before this ID */\n  endingBefore?: string;\n  /** Number of results per page (default: 10) */\n  limit?: number;\n}\n","/**\n * NFE.io SDK v3 - Service Invoices Resource\n *\n * Handles service invoice operations (NFS-e)\n * This is the core functionality of NFE.io API\n */\n\nimport type {\n  ServiceInvoiceData,\n  CreateServiceInvoiceData,\n  ListServiceInvoicesOptions,\n  ServiceInvoiceListResponse,\n  ServiceInvoiceAsyncResponse,\n  PollingOptions,\n  FlowStatus,\n  SendEmailResponse,\n} from '../types.js';\nimport type { HttpClient } from '../http/client.js';\nimport { InvoiceProcessingError, NotFoundError } from '../errors/index.js';\nimport { poll } from '../utils/polling.js';\nimport { isTerminalFlowStatus } from '../types.js';\n\n// ============================================================================\n// Types\n// ============================================================================\n\n/** Discriminated union for create() response */\nexport type CreateInvoiceResponse =\n  | { status: 'immediate'; invoice: ServiceInvoiceData }\n  | { status: 'async'; response: ServiceInvoiceAsyncResponse };\n\n/**\n * Discriminated union for cancel() response.\n *\n * Cancellation is normally asynchronous: the API replies `202 + Location` and the\n * invoice moves through `WaitingSendCancel` → `Cancelled`. Use `cancelAndWait()` to poll\n * until it settles.\n */\nexport type CancelInvoiceResponse =\n  | { status: 'immediate'; invoice: ServiceInvoiceData }\n  | { status: 'async'; response: ServiceInvoiceAsyncResponse };\n\n// ============================================================================\n// Service Invoices Resource\n// ============================================================================\n\nexport class ServiceInvoicesResource {\n  constructor(private readonly http: HttpClient) {}\n\n  // --------------------------------------------------------------------------\n  // Core CRUD Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Create a new service invoice\n   *\n   * NFE.io typically returns 202 (async processing) with a Location header.\n   * The invoice ID can be extracted from the location for polling.\n   *\n   * @param companyId - Company ID (GUID)\n   * @param data - Invoice data following NFE.io schema\n   * @returns Discriminated union: immediate (201) or async (202) response\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.serviceInvoices.create(companyId, {\n   *   borrower: {\n   *     federalTaxNumber: 12345678901234,\n   *     name: 'Client Name',\n   *     email: 'client@example.com'\n   *   },\n   *   cityServiceCode: '01234',\n   *   federalServiceCode: '01.02',\n   *   description: 'Service description',\n   *   servicesAmount: 1000.00\n   * });\n   *\n   * if (result.status === 'async') {\n   *   console.log('Invoice being processed:', result.response.invoiceId);\n   *   // Use createAndWait() or poll manually\n   * } else {\n   *   console.log('Invoice issued immediately:', result.invoice.id);\n   * }\n   * ```\n   */\n  async create(\n    companyId: string,\n    data: CreateServiceInvoiceData\n  ): Promise<CreateInvoiceResponse> {\n    const path = `/companies/${companyId}/serviceinvoices`;\n    const response = await this.http.post<ServiceInvoiceData>(path, data);\n\n    // Check for async response (202)\n    if (response.status === 202) {\n      const location = response.headers['location'] || response.headers['Location'];\n\n      if (!location) {\n        throw new InvoiceProcessingError(\n          'Async response (202) received but no Location header found',\n          { status: 202, headers: response.headers }\n        );\n      }\n\n      // Extract invoice ID from location\n      // Location format: /v1/companies/{companyId}/serviceinvoices/{invoiceId}\n      // or full URL: https://api.nfe.io/v1/companies/{companyId}/serviceinvoices/{invoiceId}\n      const invoiceId = this.extractInvoiceIdFromLocation(location);\n\n      // Keep full path for polling (with or without /v1 prefix)\n      const fullPath = location.startsWith('http') ? new URL(location).pathname : location;\n\n      return {\n        status: 'async',\n        response: {\n          code: 202,\n          status: 'pending',\n          location: fullPath,\n          invoiceId,\n        },\n      };\n    }\n\n    // Immediate success (201)\n    return {\n      status: 'immediate',\n      invoice: response.data,\n    };\n  }\n\n  /**\n   * List service invoices for a company\n   *\n   * Supports pagination and date filtering.\n   *\n   * @param companyId - Company ID (GUID)\n   * @param options - Pagination and filtering options\n   * @returns List of invoices with pagination metadata\n   *\n   * @example\n   * ```typescript\n   * // List recent invoices\n   * const result = await nfe.serviceInvoices.list(companyId, {\n   *   pageIndex: 1,\n   *   pageCount: 20,\n   *   issuedBegin: '2026-01-01',\n   *   issuedEnd: '2026-01-31'\n   * });\n   *\n   * console.log(`Found ${result.serviceInvoices?.length} invoices`);\n   * ```\n   */\n  async list(\n    companyId: string,\n    options: ListServiceInvoicesOptions = {}\n  ): Promise<ServiceInvoiceListResponse> {\n    const path = `/companies/${companyId}/serviceinvoices`;\n    const response = await this.http.get<ServiceInvoiceListResponse>(path, options as Record<string, unknown>);\n\n    return response.data;\n  }\n\n  /**\n   * Retrieve a specific service invoice by ID\n   *\n   * @param companyId - Company ID (GUID)\n   * @param invoiceId - Invoice ID (GUID)\n   * @returns Complete invoice data\n   * @throws {NotFoundError} If invoice not found\n   *\n   * @example\n   * ```typescript\n   * const invoice = await nfe.serviceInvoices.retrieve(companyId, invoiceId);\n   * console.log('Invoice status:', invoice.flowStatus);\n   * ```\n   */\n  async retrieve(\n    companyId: string,\n    invoiceId: string\n  ): Promise<ServiceInvoiceData> {\n    const path = `/companies/${companyId}/serviceinvoices/${invoiceId}`;\n    const response = await this.http.get<ServiceInvoiceData>(path);\n\n    // The API should return the invoice directly\n    if (!response.data) {\n      throw new NotFoundError(\n        `Invoice ${invoiceId} not found`,\n        { companyId, invoiceId }\n      );\n    }\n\n    return response.data;\n  }\n\n  /**\n   * Retrieve a service invoice by the caller's external id (idempotency key).\n   *\n   * @param companyId - Company ID (GUID)\n   * @param externalId - The `externalId` supplied at creation\n   * @returns The matching invoice\n   * @throws {NotFoundError} If no invoice with that external id exists\n   */\n  async retrieveByExternalId(\n    companyId: string,\n    externalId: string\n  ): Promise<ServiceInvoiceData> {\n    const path = `/companies/${companyId}/serviceinvoices/external/${externalId}`;\n    const response = await this.http.get<ServiceInvoiceData>(path);\n    if (!response.data) {\n      throw new NotFoundError(`Invoice with externalId ${externalId} not found`, {\n        companyId,\n        externalId,\n      });\n    }\n    return response.data;\n  }\n\n  /**\n   * Cancel a service invoice\n   *\n   * Cancellation is normally **asynchronous**: the API replies `202 Accepted` with a\n   * `Location` header and the invoice transitions `WaitingSendCancel` → `Cancelled`.\n   * This method returns a discriminated union (mirroring {@link create}) so the static\n   * type always matches the runtime shape. Use {@link cancelAndWait} to poll until the\n   * cancellation settles.\n   *\n   * @param companyId - Company ID (GUID)\n   * @param invoiceId - Invoice ID (GUID)\n   * @returns `{ status: 'async', response }` (202 + Location) or `{ status: 'immediate', invoice }`\n   * @throws {InvoiceProcessingError} If a 202 is returned without a Location header\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.serviceInvoices.cancel(companyId, invoiceId);\n   * if (result.status === 'async') {\n   *   console.log('Cancellation in progress:', result.response.invoiceId);\n   *   // or use cancelAndWait() to block until it settles\n   * } else {\n   *   console.log('Cancelled immediately:', result.invoice.flowStatus);\n   * }\n   * ```\n   */\n  async cancel(\n    companyId: string,\n    invoiceId: string\n  ): Promise<CancelInvoiceResponse> {\n    const path = `/companies/${companyId}/serviceinvoices/${invoiceId}`;\n    const response = await this.http.delete<ServiceInvoiceData>(path);\n\n    // Async cancellation (202 + Location) — the normal path\n    if (response.status === 202) {\n      const location = response.headers['location'] || response.headers['Location'];\n\n      if (!location) {\n        throw new InvoiceProcessingError(\n          'Async cancel response (202) received but no Location header found',\n          { status: 202, headers: response.headers }\n        );\n      }\n\n      const extractedId = this.extractInvoiceIdFromLocation(location);\n      // Keep full path for polling (with or without /v1 prefix)\n      const fullPath = location.startsWith('http') ? new URL(location).pathname : location;\n\n      return {\n        status: 'async',\n        response: {\n          code: 202,\n          status: 'pending',\n          location: fullPath,\n          invoiceId: extractedId,\n        },\n      };\n    }\n\n    // Immediate cancellation (200/201 with the invoice body)\n    return {\n      status: 'immediate',\n      invoice: response.data,\n    };\n  }\n\n  /**\n   * Cancel an invoice and wait for the cancellation to settle.\n   *\n   * Combines {@link cancel} + polling, mirroring {@link createAndWait}. Polls the invoice\n   * until it reaches a terminal flow status and returns it.\n   *\n   * @param companyId - Company ID (GUID)\n   * @param invoiceId - Invoice ID (GUID)\n   * @param options - Polling configuration (timeout, delays, callback)\n   * @returns The settled invoice (expected `flowStatus: 'Cancelled'`)\n   * @throws {TimeoutError} If polling timeout exceeded\n   * @throws {InvoiceProcessingError} If cancellation failed (`flowStatus: 'CancelFailed'`)\n   *\n   * @example\n   * ```typescript\n   * const invoice = await nfe.serviceInvoices.cancelAndWait(companyId, invoiceId);\n   * console.log(invoice.flowStatus); // 'Cancelled'\n   * ```\n   */\n  async cancelAndWait(\n    companyId: string,\n    invoiceId: string,\n    options: PollingOptions = {}\n  ): Promise<ServiceInvoiceData> {\n    const cancelResult = await this.cancel(companyId, invoiceId);\n\n    // Immediate cancellation — nothing to poll\n    if (cancelResult.status === 'immediate') {\n      return cancelResult.invoice;\n    }\n\n    const { invoiceId: targetId } = cancelResult.response;\n\n    const pollingConfig: import('../utils/polling.js').PollingOptions<ServiceInvoiceData> = {\n      fn: async () => this.retrieve(companyId, targetId),\n      isComplete: (invoice) => isTerminalFlowStatus(invoice.flowStatus as FlowStatus),\n      timeout: options.timeout ?? 120000,\n      initialDelay: options.initialDelay ?? 1000,\n      maxDelay: options.maxDelay ?? 10000,\n      backoffFactor: options.backoffFactor ?? 1.5,\n    };\n\n    if (options.onPoll) {\n      pollingConfig.onPoll = (attempt, result) => {\n        options.onPoll!(attempt, result.flowStatus as FlowStatus);\n      };\n    }\n\n    const invoice = await poll<ServiceInvoiceData>(pollingConfig);\n\n    const flowStatus = invoice.flowStatus as FlowStatus;\n    if (flowStatus === 'CancelFailed') {\n      throw new InvoiceProcessingError(\n        `Invoice cancellation failed with status: ${flowStatus}`,\n        { flowStatus, flowMessage: invoice.flowMessage, invoice }\n      );\n    }\n\n    return invoice;\n  }\n\n  // --------------------------------------------------------------------------\n  // Email Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Send invoice via email to the borrower (client)\n   *\n   * @param companyId - Company ID (GUID)\n   * @param invoiceId - Invoice ID (GUID)\n   * @returns Email send result\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.serviceInvoices.sendEmail(companyId, invoiceId);\n   * if (result.sent) {\n   *   console.log('Email sent successfully');\n   * }\n   * ```\n   */\n  async sendEmail(\n    companyId: string,\n    invoiceId: string\n  ): Promise<SendEmailResponse> {\n    const path = `/companies/${companyId}/serviceinvoices/${invoiceId}/sendemail`;\n    const response = await this.http.put<SendEmailResponse>(path);\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Async Processing Helper\n  // --------------------------------------------------------------------------\n\n  /**\n   * Create invoice and wait for completion (handles async processing automatically)\n   *\n   * This method combines create() + polling to provide a synchronous-like experience.\n   * It uses exponential backoff and respects timeout constraints.\n   *\n   * @param companyId - Company ID (GUID)\n   * @param data - Invoice data\n   * @param options - Polling configuration (timeout, delays, callbacks)\n   * @returns Completed invoice (Issued status)\n   * @throws {TimeoutError} If polling timeout exceeded\n   * @throws {InvoiceProcessingError} If invoice processing failed\n   *\n   * @example\n   * ```typescript\n   * // Simple usage with defaults (2 min timeout)\n   * const invoice = await nfe.serviceInvoices.createAndWait(companyId, data);\n   * console.log('Invoice issued:', invoice.id);\n   *\n   * // Custom timeout and progress tracking\n   * const invoice = await nfe.serviceInvoices.createAndWait(companyId, data, {\n   *   timeout: 180000, // 3 minutes\n   *   onPoll: (attempt, status) => {\n   *     console.log(`Attempt ${attempt}: ${status}`);\n   *   }\n   * });\n   * ```\n   */\n  async createAndWait(\n    companyId: string,\n    data: CreateServiceInvoiceData,\n    options: PollingOptions = {}\n  ): Promise<ServiceInvoiceData> {\n    // Create invoice\n    const createResult = await this.create(companyId, data);\n\n    // If immediate success (201), return directly\n    if (createResult.status === 'immediate') {\n      return createResult.invoice;\n    }\n\n    // Handle async response (202) - poll until complete\n    const { invoiceId } = createResult.response;\n\n    // Build polling config\n    const pollingConfig: import('../utils/polling.js').PollingOptions<ServiceInvoiceData> = {\n      fn: async () => this.retrieve(companyId, invoiceId),\n      isComplete: (invoice) => {\n        const flowStatus = invoice.flowStatus as FlowStatus;\n        return isTerminalFlowStatus(flowStatus);\n      },\n      timeout: options.timeout ?? 120000, // 2 minutes default\n      initialDelay: options.initialDelay ?? 1000, // 1 second\n      maxDelay: options.maxDelay ?? 10000, // 10 seconds\n      backoffFactor: options.backoffFactor ?? 1.5,\n    };\n\n    // Add onPoll callback if provided\n    if (options.onPoll) {\n      pollingConfig.onPoll = (attempt, result) => {\n        const flowStatus = result.flowStatus as FlowStatus;\n        options.onPoll!(attempt, flowStatus);\n      };\n    }\n\n    // Use polling utility from Phase 1\n    const invoice = await poll<ServiceInvoiceData>(pollingConfig);\n\n    // Check if processing failed\n    const flowStatus = invoice.flowStatus as FlowStatus;\n    if (flowStatus === 'IssueFailed' || flowStatus === 'CancelFailed') {\n      throw new InvoiceProcessingError(\n        `Invoice processing failed with status: ${flowStatus}`,\n        {\n          flowStatus,\n          flowMessage: invoice.flowMessage,\n          invoice,\n        }\n      );\n    }\n\n    return invoice;\n  }\n\n  // --------------------------------------------------------------------------\n  // File Downloads\n  // --------------------------------------------------------------------------\n\n  /**\n   * Download invoice PDF\n   *\n   * Downloads the PDF file for a service invoice. The invoice must be in a terminal state\n   * (Issued, Cancelled) before the PDF is available.\n   *\n   * @param companyId - Company ID (GUID)\n   * @param invoiceId - Invoice ID (GUID) — obrigatório\n   * @returns PDF data as Buffer\n   * @throws {NotFoundError} If the invoice or PDF is not found/not ready\n   * @throws {AuthenticationError} If API key is invalid\n   *\n   * @example\n   * ```typescript\n   * const pdf = await nfe.serviceInvoices.downloadPdf(companyId, invoiceId);\n   * fs.writeFileSync('invoice.pdf', pdf);\n   * ```\n   *\n   * @remarks\n   * - PDF is only available after invoice reaches terminal state (Issued/Cancelled)\n   * - Returns 404 if PDF is not yet ready - use polling or check flowStatus first\n   * - Large files may consume significant memory - consider streaming for production use\n   *\n   * Não existe download em lote por empresa. Até 2026-09-02 `invoiceId` era\n   * opcional e o ramo sem id montava `/serviceinvoices/pdf`, que o servidor casa\n   * com a rota `/{id}` e trata como identificador literal:\n   * `404 \"service invoice with id (pdf) was not found\"`. A rota não está na spec\n   * `nf-servico-v1` nem no `nfeio-docs` — nunca houve caminho válido.\n   */\n  async downloadPdf(companyId: string, invoiceId: string): Promise<Buffer> {\n    const response = await this.http.get<Buffer>(\n      `/companies/${companyId}/serviceinvoices/${invoiceId}/pdf`,\n      undefined,\n      { Accept: 'application/pdf' }\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Download invoice XML\n   *\n   * Downloads the XML file for a service invoice. The invoice must be in a terminal state\n   * (Issued, Cancelled) before the XML is available.\n   *\n   * @param companyId - Company ID (GUID)\n   * @param invoiceId - Invoice ID (GUID) — obrigatório\n   * @returns XML data as Buffer\n   * @throws {NotFoundError} If the invoice or XML is not found/not ready\n   * @throws {AuthenticationError} If API key is invalid\n   *\n   * @example\n   * ```typescript\n   * const xml = await nfe.serviceInvoices.downloadXml(companyId, invoiceId);\n   * fs.writeFileSync('invoice.xml', xml);\n   * console.log(xml.toString('utf-8')); // View as string\n   * ```\n   *\n   * @remarks\n   * - XML is only available after invoice reaches terminal state (Issued/Cancelled)\n   * - Returns 404 if XML is not yet ready - use polling or check flowStatus first\n   * - Buffer can be converted to string with `.toString('utf-8')` if needed\n   *\n   * Não existe download em lote por empresa — mesmo motivo do\n   * {@link ServiceInvoicesResource.downloadPdf}: `/serviceinvoices/xml` responde\n   * `404 \"service invoice with id (xml) was not found\"`.\n   */\n  async downloadXml(companyId: string, invoiceId: string): Promise<Buffer> {\n    const response = await this.http.get<Buffer>(\n      `/companies/${companyId}/serviceinvoices/${invoiceId}/xml`,\n      undefined,\n      { Accept: 'application/xml' }\n    );\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // High-level Convenience Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Get invoice status with detailed information\n   *\n   * @param companyId - Company ID (GUID)\n   * @param invoiceId - Invoice ID (GUID)\n   * @returns Status information with invoice data\n   */\n  async getStatus(companyId: string, invoiceId: string): Promise<{\n    status: FlowStatus;\n    invoice: ServiceInvoiceData;\n    isComplete: boolean;\n    isFailed: boolean;\n  }> {\n    const invoice = await this.retrieve(companyId, invoiceId);\n    const status = (invoice.flowStatus as FlowStatus) ?? 'WaitingSend';\n\n    return {\n      status,\n      invoice,\n      isComplete: isTerminalFlowStatus(status),\n      isFailed: ['CancelFailed', 'IssueFailed'].includes(status),\n    };\n  }\n\n  /**\n   * Bulk operations: Create multiple invoices\n   *\n   * @param companyId - Company ID (GUID)\n   * @param invoices - Array of invoice data\n   * @param options - Batch processing options\n   * @returns Array of create responses\n   */\n  async createBatch(\n    companyId: string,\n    invoices: CreateServiceInvoiceData[],\n    options: {\n      waitForCompletion?: boolean;\n      maxConcurrent?: number;\n    } = {}\n  ): Promise<Array<CreateInvoiceResponse | ServiceInvoiceData>> {\n    const { waitForCompletion = false, maxConcurrent = 5 } = options;\n\n    // Process in batches to avoid overwhelming the API\n    const results: Array<CreateInvoiceResponse | ServiceInvoiceData> = [];\n\n    for (let i = 0; i < invoices.length; i += maxConcurrent) {\n      const batch = invoices.slice(i, i + maxConcurrent);\n\n      const batchPromises = batch.map(async (invoiceData) => {\n        if (waitForCompletion) {\n          return this.createAndWait(companyId, invoiceData);\n        } else {\n          return this.create(companyId, invoiceData);\n        }\n      });\n\n      const batchResults = await Promise.all(batchPromises);\n      results.push(...batchResults);\n    }\n\n    return results;\n  }\n\n  // --------------------------------------------------------------------------\n  // Private Helper Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Extract invoice ID from Location header\n   * Location format: /v1/companies/{companyId}/serviceinvoices/{invoiceId}\n   */\n  private extractInvoiceIdFromLocation(location: string): string {\n    const match = location.match(/serviceinvoices\\/([a-z0-9-]+)/i);\n\n    if (!match || !match[1]) {\n      throw new InvoiceProcessingError(\n        'Could not extract invoice ID from Location header',\n        { location }\n      );\n    }\n\n    return match[1];\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\nexport function createServiceInvoicesResource(http: HttpClient): ServiceInvoicesResource {\n  return new ServiceInvoicesResource(http);\n}\n","/**\n * NFE.io SDK v3 - Certificate Validator\n *\n * Utilities for validating digital certificates before upload\n * Supports PKCS#12 format (.pfx, .p12)\n */\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport interface CertificateMetadata {\n  subject: string;\n  issuer: string;\n  validFrom: Date;\n  validTo: Date;\n  serialNumber?: string;\n}\n\nexport interface CertificateValidationResult {\n  valid: boolean;\n  metadata?: CertificateMetadata;\n  error?: string;\n}\n\n// ============================================================================\n// Certificate Validator\n// ============================================================================\n\nexport class CertificateValidator {\n  /**\n   * Pre-flight a certificate file before upload.\n   *\n   * IMPORTANT: this performs **format-only** local checks (non-empty buffer,\n   * password provided, PKCS#12 `3082` magic bytes). It does NOT parse the\n   * certificate and CANNOT verify the password, expiry, subject or issuer —\n   * doing so requires a PKCS#12 reader, which would violate the SDK's\n   * no-runtime-dependency rule. Subject/issuer/validity and the password are\n   * verified **server-side** by the NFE.io API when the certificate is uploaded.\n   *\n   * Therefore a `valid: true` result means \"looks like a PKCS#12 file\", not\n   * \"this is a valid, in-date certificate with the right password\".\n   *\n   * @param file - Certificate file buffer\n   * @param password - Certificate password (presence checked only)\n   * @returns Pre-flight result (no fabricated metadata)\n   */\n  static async validate(\n    file: Buffer,\n    password: string\n  ): Promise<CertificateValidationResult> {\n    try {\n      // Basic validation - check file format\n      if (!Buffer.isBuffer(file) || file.length === 0) {\n        return { valid: false, error: 'Invalid file buffer' };\n      }\n\n      // Check password is provided\n      if (!password || password.trim().length === 0) {\n        return { valid: false, error: 'Password is required' };\n      }\n\n      // Check PKCS#12 signature (basic format validation)\n      // PKCS#12 files typically start with specific bytes\n      const signature = file.toString('hex', 0, 2);\n      if (signature !== '3082') {\n        return { valid: false, error: 'Invalid certificate format. Expected PKCS#12 (.pfx/.p12)' };\n      }\n\n      // Format pre-flight passed. We deliberately DO NOT return metadata:\n      // full PKCS#12 parsing (subject/issuer/validity) and password verification\n      // require a runtime dependency we don't take. The API validates these on\n      // upload. Returning fabricated metadata here would lie about validation.\n      return { valid: true };\n\n    } catch (error) {\n      if (error instanceof Error) {\n        // Common error messages\n        if (error.message.includes('password') || error.message.includes('MAC')) {\n          return { valid: false, error: 'Invalid certificate password' };\n        }\n        if (error.message.includes('parse') || error.message.includes('format')) {\n          return { valid: false, error: 'Invalid certificate format' };\n        }\n      }\n\n      return {\n        valid: false,\n        error: error instanceof Error ? error.message : 'Invalid certificate or password'\n      };\n    }\n  }\n\n  /**\n   * Check if certificate format is supported\n   *\n   * @param filename - Certificate filename\n   * @returns True if .pfx or .p12 format\n   */\n  static isSupportedFormat(filename: string): boolean {\n    const ext = filename.toLowerCase().split('.').pop();\n    return ext === 'pfx' || ext === 'p12';\n  }\n\n  /**\n   * Calculate days until expiration\n   *\n   * @param expiresOn - Expiration date\n   * @returns Number of days until expiration (negative if expired)\n   */\n  static getDaysUntilExpiration(expiresOn: Date): number {\n    const now = new Date();\n    const diff = expiresOn.getTime() - now.getTime();\n    return Math.floor(diff / (1000 * 60 * 60 * 24));\n  }\n\n  /**\n   * Check if certificate is expiring soon\n   *\n   * @param expiresOn - Expiration date\n   * @param threshold - Days threshold (default: 30)\n   * @returns True if expiring within threshold days\n   */\n  static isExpiringSoon(expiresOn: Date, threshold: number = 30): boolean {\n    const days = this.getDaysUntilExpiration(expiresOn);\n    return days >= 0 && days < threshold;\n  }\n}\n","/**\n * NFE.io SDK v3 - Companies Resource\n *\n * Handles company operations and certificate management\n */\n\nimport type {\n  Company,\n  CompanyResourceItem,\n  CompanyV2ListOptions,\n  CompanyV2ListResponse,\n  CertificateMetadataResourceItem,\n  CertificatesMetadataResource,\n  CompanyCertificateV1,\n  ListResponse,\n  PaginationOptions\n} from '../types.js';\nimport type { HttpClient } from '../http/client.js';\nimport { ValidationError, NotFoundError } from '../errors/index.js';\nimport { CertificateValidator } from '../utils/certificate-validator.js';\n\n// Page size for listAll/listIterator: the API caps GET /companies at\n// pageCount 50 (values above 50 — and also 1 — are rejected with a 400).\nconst AUTO_PAGINATION_PAGE_SIZE = 50;\n\n/**\n * Resumo do certificado de uma empresa.\n *\n * `expiresOn` / `isValid` / os dois derivados descrevem o certificado preferido\n * (ver {@link CompaniesResource.getCertificateStatus}); `certificates` traz os itens\n * como a API devolveu, para quem precisar de `thumbprint`, `subject` ou decidir\n * por outro critério.\n */\nexport interface CertificateStatusSummary {\n  /** Há ao menos um certificado instalado. */\n  hasCertificate: boolean;\n  /** Vencimento do certificado preferido (o `validUntil` da API). */\n  expiresOn?: string;\n  /** O certificado preferido está com `status: 'Active'`. */\n  isValid?: boolean;\n  /** Dias até o vencimento — negativo se já venceu. */\n  daysUntilExpiration?: number;\n  /** Vence dentro do limite padrão do {@link CertificateValidator} (30 dias). */\n  isExpiringSoon?: boolean;\n  /** Itens como a API os devolveu. Vazio quando não há certificado. */\n  certificates: readonly CertificateMetadataResourceItem[];\n}\n\n/**\n * Escolhe o certificado que o resumo descreve: um ativo, o de vencimento mais\n * distante; sem nenhum ativo, o de vencimento mais distante entre todos.\n */\nfunction pickPreferredCertificate(\n  certificates: readonly CertificateMetadataResourceItem[]\n): CertificateMetadataResourceItem | undefined {\n  if (certificates.length === 0) return undefined;\n\n  const byLatestExpiry = (\n    a: CertificateMetadataResourceItem,\n    b: CertificateMetadataResourceItem\n  ): number => new Date(b.validUntil ?? 0).getTime() - new Date(a.validUntil ?? 0).getTime();\n\n  const active = certificates.filter(c => c.status === 'Active');\n  const pool = active.length > 0 ? active : certificates;\n  return [...pool].sort(byLatestExpiry)[0];\n}\n\n/** Monta o resumo a partir dos itens de `/v1/companies/{id}/certificate`. */\nfunction summarizeCertificates(\n  certificates: readonly CertificateMetadataResourceItem[]\n): CertificateStatusSummary {\n  const preferred = pickPreferredCertificate(certificates);\n\n  if (!preferred) {\n    return { hasCertificate: false, certificates };\n  }\n\n  const summary: CertificateStatusSummary = {\n    hasCertificate: true,\n    isValid: preferred.status === 'Active',\n    certificates,\n  };\n\n  // `validUntil` é obrigatório na spec, mas o SDK não decide por ela: sem data,\n  // devolve o que dá para afirmar em vez de emitir um `Invalid Date`.\n  if (preferred.validUntil) {\n    const expirationDate = new Date(preferred.validUntil);\n    summary.expiresOn = preferred.validUntil;\n    summary.daysUntilExpiration = CertificateValidator.getDaysUntilExpiration(expirationDate);\n    summary.isExpiringSoon = CertificateValidator.isExpiringSoon(expirationDate);\n  }\n\n  return summary;\n}\n\n/**\n * Lê o certificado que o item da listagem de empresas v1 já traz.\n *\n * Existe para que a varredura por conta não faça uma requisição por empresa: numa\n * conta com centenas de empresas isso é indistinguível de travamento. O campo vem\n * em todo item de `GET /v1/companies` (medido em 2026-09-02).\n */\nfunction readListedCertificate(company: Company): CompanyCertificateV1 | undefined {\n  const certificate = (company as { certificate?: unknown }).certificate;\n  if (!certificate || typeof certificate !== 'object') return undefined;\n  return certificate as CompanyCertificateV1;\n}\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Validate CNPJ format (14 digits) with check digits\n */\nfunction validateCNPJ(cnpj: number): boolean {\n  const cnpjStr = cnpj.toString().padStart(14, '0');\n  if (cnpjStr.length !== 14) return false;\n  if (/^(\\d)\\1{13}$/.test(cnpjStr)) return false; // All same digits\n\n  // Validate first check digit\n  let sum = 0;\n  let weight = 5;\n  for (let i = 0; i < 12; i++) {\n    sum += parseInt(cnpjStr[i]!) * weight;\n    weight = weight === 2 ? 9 : weight - 1;\n  }\n  const firstDigit = sum % 11 < 2 ? 0 : 11 - (sum % 11);\n  if (firstDigit !== parseInt(cnpjStr[12]!)) return false;\n\n  // Validate second check digit\n  sum = 0;\n  weight = 6;\n  for (let i = 0; i < 13; i++) {\n    sum += parseInt(cnpjStr[i]!) * weight;\n    weight = weight === 2 ? 9 : weight - 1;\n  }\n  const secondDigit = sum % 11 < 2 ? 0 : 11 - (sum % 11);\n  if (secondDigit !== parseInt(cnpjStr[13]!)) return false;\n\n  return true;\n}\n\n/**\n * Validate CPF format (11 digits) with check digits\n */\nfunction validateCPF(cpf: number): boolean {\n  const cpfStr = cpf.toString().padStart(11, '0');\n  if (cpfStr.length !== 11) return false;\n  if (/^(\\d)\\1{10}$/.test(cpfStr)) return false; // All same digits\n\n  // Validate first check digit\n  let sum = 0;\n  for (let i = 0; i < 9; i++) {\n    sum += parseInt(cpfStr[i]!) * (10 - i);\n  }\n  const firstDigit = sum % 11 < 2 ? 0 : 11 - (sum % 11);\n  if (firstDigit !== parseInt(cpfStr[9]!)) return false;\n\n  // Validate second check digit\n  sum = 0;\n  for (let i = 0; i < 10; i++) {\n    sum += parseInt(cpfStr[i]!) * (11 - i);\n  }\n  const secondDigit = sum % 11 < 2 ? 0 : 11 - (sum % 11);\n  if (secondDigit !== parseInt(cpfStr[10]!)) return false;\n\n  return true;\n}\n\n/**\n * Validate company data before API call\n */\nfunction validateCompanyData(data: Partial<Company>): void {\n  // Validate required fields for creation\n  if ('federalTaxNumber' in data) {\n    const taxNumber = data.federalTaxNumber;\n    if (typeof taxNumber !== 'number') {\n      throw new ValidationError('federalTaxNumber must be a number');\n    }\n\n    const length = taxNumber.toString().length;\n    if (length === 14) {\n      if (!validateCNPJ(taxNumber)) {\n        throw new ValidationError('Invalid CNPJ format. Must be 14 digits and not all same digit.');\n      }\n    } else if (length === 11) {\n      if (!validateCPF(taxNumber)) {\n        throw new ValidationError('Invalid CPF format. Must be 11 digits and not all same digit.');\n      }\n    } else {\n      throw new ValidationError('federalTaxNumber must be 11 digits (CPF) or 14 digits (CNPJ)');\n    }\n  }\n\n  // Validate email format if provided\n  if (data.email && typeof data.email === 'string') {\n    const emailRegex = /^[^\\s@]+@[^\\s@]+\\.[^\\s@]+$/;\n    if (!emailRegex.test(data.email)) {\n      throw new ValidationError('Invalid email format');\n    }\n  }\n}\n\n// ============================================================================\n// Companies Resource\n// ============================================================================\n\nexport class CompaniesResource {\n  /**\n   * @param http - Main client (api.nfe.io) for the legacy v1 company CRUD.\n   * @param v2Http - Optional client for the contribuintes-v2 endpoints on\n   *   api.nfse.io (e.g. the HEAD existence check). Falls back to `http`.\n   */\n  constructor(\n    private readonly http: HttpClient,\n    private readonly v2Http: HttpClient = http\n  ) {}\n\n  // --------------------------------------------------------------------------\n  // Core CRUD Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Check whether a company exists, via `HEAD /v2/companies/{id}` (api.nfse.io).\n   *\n   * @returns `true` if the company exists (2xx), `false` on 404. Other errors propagate.\n   */\n  async exists(companyId: string): Promise<boolean> {\n    if (!companyId || companyId.trim() === '') {\n      throw new ValidationError('Company ID is required');\n    }\n    try {\n      await this.v2Http.head(`/v2/companies/${companyId}`);\n      return true;\n    } catch (error) {\n      if (error instanceof NotFoundError) return false;\n      throw error;\n    }\n  }\n\n  /**\n   * Create a new company\n   *\n   * The API requires `name`, `federalTaxNumber`, `taxRegime` and `address`\n   * (with `state`, `city { code, name }`, `district`, `street`, `number`,\n   * `postalCode`, `country`) — a payload without them compiles against the\n   * loose `Company`-based signature but fails with a 400. Note that `email`\n   * is NOT part of the create body. For the strict wire shape, see\n   * {@link CreateCompanyResourceItem} (exported from the package root).\n   *\n   * @param data - Company data (excluding id, createdOn, modifiedOn)\n   * @returns The created company with generated id\n   * @throws {ValidationError} If company data is invalid\n   * @throws {AuthenticationError} If API key is invalid\n   * @throws {ConflictError} If company with same tax number already exists\n   *\n   * @example\n   * ```typescript\n   * const company = await nfe.companies.create({\n   *   name: 'Acme Corp',\n   *   federalTaxNumber: 12345678000190,\n   *   taxRegime: 'SimplesNacional',\n   *   address: {\n   *     state: 'SP',\n   *     city: { code: '3550308', name: 'São Paulo' },\n   *     district: 'Centro',\n   *     street: 'Rua Exemplo',\n   *     number: '100',\n   *     postalCode: '01001000',\n   *     country: 'BRA',\n   *   },\n   * });\n   * ```\n   */\n  async create(data: Omit<Company, 'id' | 'createdOn' | 'modifiedOn'>): Promise<Company> {\n    // Validate data before API call\n    validateCompanyData(data);\n\n    const path = '/companies';\n    const response = await this.http.post<{ companies: Company }>(path, data);\n\n    // API returns wrapped object: { companies: {...} }\n    return response.data.companies;\n  }\n\n  /**\n   * List companies (v1 API — offset pagination)\n   *\n   * @deprecated The v1 companies API (`api.nfe.io/v1/companies`) is being\n   * discontinued. Prefer {@link listV2} (cursor-based, `api.nfse.io/v2`) for\n   * page-by-page listing, or {@link listAll}/{@link listIterator} for full\n   * sweeps. This method keeps working during the coexistence window.\n   *\n   * Pagination is 1-based (API contract): the first page is `pageIndex: 1`.\n   * The API rejects `pageIndex: 0` with a validation error.\n   *\n   * `pageCount` accepted by the API: 2-50 (when omitted, the API returns 10\n   * items). Values outside that range — including 1, despite the API's\n   * \"between 1 and 50\" error message — are rejected with a 400.\n   *\n   * @param options - Pagination options (pageCount, pageIndex)\n   * @returns List response with companies and pagination info\n   *\n   * @example\n   * ```typescript\n   * const page1 = await nfe.companies.list({ pageCount: 20, pageIndex: 1 });\n   * const page2 = await nfe.companies.list({ pageCount: 20, pageIndex: 2 });\n   * ```\n   */\n  async list(options: PaginationOptions = {}): Promise<ListResponse<Company>> {\n    const path = '/companies';\n    const response = await this.http.get<{ companies: Company[]; page: number }>(path, options);\n\n    // API returns: { companies: [...], page: number }\n    // Transform to our standard ListResponse format (pageIndex stays 1-based, as on the wire)\n    return {\n      data: response.data.companies,\n      page: {\n        pageIndex: response.data.page,\n        pageCount: options.pageCount ?? 10, // the API returns 10 items when pageCount is omitted\n      }\n    };\n  }\n\n  /**\n   * List companies via the v2 cursor API (`GET api.nfse.io/v2/companies`)\n   *\n   * This is the successor of {@link list} (the v1 companies API is being\n   * discontinued). Cursor-based: pass the last item's `id` as\n   * `startingAfter` to fetch the next page; `hasMore` tells whether more\n   * pages exist. Results are ordered by name, then id.\n   *\n   * `limit` accepted by the API: 1-50 (default 10). Values above 50 are\n   * rejected; `limit: 0` is rejected client-side (the API would silently\n   * return an empty page). Items follow the **v2 projection**\n   * ({@link CompanyResourceItem}) — a different shape from the v1\n   * {@link Company} (no NFS-e config fields; adds `stateTaxes`,\n   * `municipalTaxes`, `type`, `version`).\n   *\n   * Known API issue (reported 2026-07-14): on some accounts, specific\n   * records make the server answer 500 for any page window containing\n   * them, which breaks full sweeps — the reason {@link listAll}/\n   * {@link listIterator} still run on v1 in this release.\n   *\n   * @param options - Cursor pagination options (limit, startingAfter, endingBefore)\n   * @returns Page of companies (v2 projection) plus `hasMore`\n   * @throws {ValidationError} If `limit` is outside 1-50\n   *\n   * @example\n   * ```typescript\n   * let page = await nfe.companies.listV2({ limit: 50 });\n   * while (page.hasMore) {\n   *   const last = page.data[page.data.length - 1];\n   *   page = await nfe.companies.listV2({ limit: 50, startingAfter: last.id });\n   * }\n   * ```\n   */\n  async listV2(options: CompanyV2ListOptions = {}): Promise<CompanyV2ListResponse> {\n    if (options.limit !== undefined && (options.limit < 1 || options.limit > 50)) {\n      throw new ValidationError('limit must be between 1 and 50');\n    }\n\n    const params: Record<string, unknown> = {};\n    if (options.limit !== undefined) params.limit = options.limit;\n    if (options.startingAfter) params.startingAfter = options.startingAfter;\n    if (options.endingBefore) params.endingBefore = options.endingBefore;\n\n    // Wire response: { hasMore, companies } (the spec omits hasMore; the live API sends it)\n    const response = await this.v2Http.get<{\n      hasMore?: boolean;\n      companies?: CompanyResourceItem[] | null;\n    }>('/v2/companies', params);\n\n    return {\n      data: (response.data.companies ?? []) as CompanyResourceItem[],\n      hasMore: response.data.hasMore ?? false,\n    };\n  }\n\n  /**\n   * List all companies with automatic pagination\n   *\n   * Fetches all pages automatically and returns complete list.\n   * Use with caution for accounts with many companies.\n   *\n   * @returns Array of all companies\n   *\n   * @example\n   * ```typescript\n   * const allCompanies = await nfe.companies.listAll();\n   * console.log(`Total companies: ${allCompanies.length}`);\n   * ```\n   */\n  async listAll(): Promise<Company[]> {\n    const companies: Company[] = [];\n    let pageIndex = 1; // pagination is 1-based; the API rejects pageIndex 0\n    let hasMore = true;\n\n    while (hasMore) {\n      const page = await this.list({ pageCount: AUTO_PAGINATION_PAGE_SIZE, pageIndex });\n      const pageData = Array.isArray(page) ? page : (page.data || []);\n      companies.push(...pageData);\n\n      // Check if there are more pages\n      hasMore = pageData.length === AUTO_PAGINATION_PAGE_SIZE;\n      pageIndex++;\n    }\n\n    return companies;\n  }\n\n  /**\n   * Async iterator for streaming companies\n   *\n   * Memory-efficient way to process large numbers of companies.\n   * Automatically fetches new pages as needed.\n   *\n   * @yields Company objects one at a time\n   *\n   * @example\n   * ```typescript\n   * for await (const company of nfe.companies.listIterator()) {\n   *   console.log(company.name);\n   * }\n   * ```\n   */\n  async *listIterator(): AsyncIterableIterator<Company> {\n    let pageIndex = 1; // pagination is 1-based; the API rejects pageIndex 0\n    let hasMore = true;\n\n    while (hasMore) {\n      const page = await this.list({ pageCount: AUTO_PAGINATION_PAGE_SIZE, pageIndex });\n      const pageData = Array.isArray(page) ? page : (page.data || []);\n\n      for (const company of pageData) {\n        yield company;\n      }\n\n      hasMore = pageData.length === AUTO_PAGINATION_PAGE_SIZE;\n      pageIndex++;\n    }\n  }\n\n  /**\n   * Retrieve a specific company by ID\n   *\n   * @param companyId - Company ID to retrieve\n   * @returns The company data\n   * @throws {NotFoundError} If company doesn't exist\n   * @throws {AuthenticationError} If API key is invalid\n   *\n   * @example\n   * ```typescript\n   * const company = await nfe.companies.retrieve('company-123');\n   * console.log(company.name);\n   * ```\n   */\n  async retrieve(companyId: string): Promise<Company> {\n    const path = `/companies/${companyId}`;\n    const response = await this.http.get<{ companies: Company }>(path);\n\n    // API returns wrapped object: { companies: {...} }\n    return response.data.companies;\n  }\n\n  /**\n   * Update a company\n   *\n   * **This is a PUT (full replacement), NOT a partial update.** The API\n   * requires the complete object (`name`, `federalTaxNumber`, `taxRegime`,\n   * `address`, ...) on every call; omitted fields are reset/replaced, not\n   * kept. Sending only the fields you want to change either fails with a\n   * 400 or silently wipes the rest. Always read-modify-write.\n   *\n   * For the strict wire shape, see {@link UpdateCompanyResourceItem}\n   * (exported from the package root). The loose `Partial<Company>`\n   * signature is kept for backwards compatibility only.\n   *\n   * @param companyId - Company ID to update\n   * @param data - The COMPLETE company data (full replacement)\n   * @returns The updated company\n   * @throws {ValidationError} If update data is invalid\n   * @throws {NotFoundError} If company doesn't exist\n   *\n   * @example\n   * ```typescript\n   * // Read-modify-write: fetch the current object, change it, send it whole\n   * const current = await nfe.companies.retrieve('company-123');\n   * const updated = await nfe.companies.update('company-123', {\n   *   ...current,\n   *   tradeName: 'Novo Nome Fantasia',\n   * });\n   * ```\n   */\n  async update(companyId: string, data: Partial<Company>): Promise<Company> {\n    // Validate update data\n    validateCompanyData(data);\n\n    const path = `/companies/${companyId}`;\n    const response = await this.http.put<{ companies: Company }>(path, data);\n\n    // API returns wrapped object: { companies: {...} }\n    return response.data.companies;\n  }\n\n  /**\n   * Delete a company (named 'remove' to avoid JS keyword conflict)\n   *\n   * @param companyId - Company ID to delete\n   * @returns Deletion confirmation with company ID\n   * @throws {NotFoundError} If company doesn't exist\n   * @throws {ConflictError} If company has dependent resources\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.companies.remove('company-123');\n   * console.log(`Deleted: ${result.deleted}`); // true\n   * ```\n   */\n  async remove(companyId: string): Promise<{ deleted: boolean; id: string }> {\n    const path = `/companies/${companyId}`;\n    const response = await this.http.delete<{ deleted: boolean; id: string }>(path);\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Certificate Management\n  // --------------------------------------------------------------------------\n\n  /**\n   * Validate certificate before upload\n   *\n   * @param file - Certificate file buffer\n   * @param password - Certificate password\n   * @returns Validation result with metadata\n   * @throws {ValidationError} If certificate format is not supported\n   *\n   * @example\n   * ```typescript\n   * const validation = await nfe.companies.validateCertificate(\n   *   certificateBuffer,\n   *   'password123'\n   * );\n   *\n   * if (validation.valid) {\n   *   console.log('Certificate expires:', validation.metadata?.validTo);\n   * } else {\n   *   console.error('Invalid certificate:', validation.error);\n   * }\n   * ```\n   */\n  async validateCertificate(\n    file: Buffer,\n    password: string\n  ): Promise<{\n    valid: boolean;\n    metadata?: {\n      subject: string;\n      issuer: string;\n      validFrom: Date;\n      validTo: Date;\n      serialNumber?: string;\n    };\n    error?: string;\n  }> {\n    return await CertificateValidator.validate(file, password);\n  }\n\n  /**\n   * Upload digital certificate for a company\n   * Automatically validates certificate before upload\n   *\n   * @param companyId - Company ID\n   * @param certificateData - Certificate data\n   * @returns Upload result\n   * @throws {ValidationError} If certificate is invalid or password is wrong\n   * @throws {NotFoundError} If company doesn't exist\n   *\n   * @example\n   * ```typescript\n   * import { readFileSync } from 'fs';\n   *\n   * const certificateBuffer = readFileSync('certificate.pfx');\n   *\n   * const result = await nfe.companies.uploadCertificate('company-123', {\n   *   file: certificateBuffer,\n   *   password: 'cert-password',\n   *   filename: 'certificate.pfx'\n   * });\n   *\n   * console.log(result.message);\n   * ```\n   */\n  async uploadCertificate(\n    companyId: string,\n    certificateData: {\n      /** Certificate file (Buffer or Blob) */\n      file: any;\n      /** Certificate password */\n      password: string;\n      /** Optional filename (should be .pfx or .p12) */\n      filename?: string;\n    }\n  ): Promise<{ uploaded: boolean; message?: string }> {\n    // Validate filename format if provided\n    if (certificateData.filename && !CertificateValidator.isSupportedFormat(certificateData.filename)) {\n      throw new ValidationError(\n        'Unsupported certificate format. Only .pfx and .p12 files are supported.'\n      );\n    }\n\n    // Pre-validate certificate if it's a Buffer\n    if (Buffer.isBuffer(certificateData.file)) {\n      const validation = await CertificateValidator.validate(\n        certificateData.file,\n        certificateData.password\n      );\n\n      if (!validation.valid) {\n        throw new ValidationError(\n          `Certificate validation failed: ${validation.error}`\n        );\n      }\n    }\n\n    const path = `/companies/${companyId}/certificate`;\n\n    // Create FormData for file upload\n    const formData = this.createFormData();\n\n    // Field name MUST be `file`: the API binds this multipart field and rejects\n    // anything else with 400 `{\"errors\":{\"file\":[\"The File field is required.\"]}}`.\n    // Verified live on 2026-09-01 — the previous name (`certificate`) meant this\n    // method could never succeed. See tests/fixtures/live-contracts/certificate-upload-field.json.\n    if (certificateData.filename) {\n      formData.append('file', certificateData.file, certificateData.filename);\n    } else {\n      formData.append('file', certificateData.file);\n    }\n\n    // Add password\n    formData.append('password', certificateData.password);\n\n    const response = await this.http.post<{ uploaded: boolean; message?: string }>(\n      path,\n      formData\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Get certificate status for a company\n   * Includes expiration calculation and warnings\n   *\n   * @param companyId - Company ID\n   * @returns Certificate status with expiration info\n   * @throws {NotFoundError} If company doesn't exist\n   *\n   * @remarks\n   * `GET /v1/companies/{id}/certificate` responde `{ certificates: [...] }`, com\n   * `validUntil` e `status` em cada item — NÃO `{hasCertificate, expiresOn, isValid}`,\n   * que era o que este método lia antes de 2026-09-02 (e por isso devolvia\n   * `undefined` em tudo, silenciosamente). Empresa sem certificado responde\n   * **200 com `certificates: []`**, não 404.\n   *\n   * O campo de vencimento na superfície do SDK se chama `expiresOn` — o mesmo nome\n   * que a API usa quando o certificado vem embutido no item da listagem de empresas\n   * ({@link CompanyCertificateV1}). No endpoint de certificado ele se chama\n   * `validUntil`; a normalização acontece aqui.\n   *\n   * Quando há mais de um certificado, o resumo descreve o preferido: um com\n   * `status: 'Active'` e, entre os ativos, o de vencimento mais distante. Se nenhum\n   * for ativo, o de vencimento mais distante entre todos. Isso é convenção do SDK,\n   * não contrato da API — use `certificates` para decidir de outro jeito.\n   *\n   * @example\n   * ```typescript\n   * const status = await nfe.companies.getCertificateStatus('company-123');\n   *\n   * if (status.hasCertificate) {\n   *   console.log('Certificate expires:', status.expiresOn);\n   *   console.log('Days until expiration:', status.daysUntilExpiration);\n   *\n   *   if (status.isExpiringSoon) {\n   *     console.warn('Certificate is expiring soon!');\n   *   }\n   *\n   *   // Dado que o resumo não expõe: thumbprint, subject, providerType...\n   *   console.log(status.certificates[0]?.thumbprint);\n   * }\n   * ```\n   */\n  async getCertificateStatus(companyId: string): Promise<CertificateStatusSummary> {\n    const path = `/companies/${companyId}/certificate`;\n    const response = await this.http.get<CertificatesMetadataResource>(path);\n\n    const certificates = response.data?.certificates ?? [];\n    return summarizeCertificates(certificates);\n  }\n\n  /**\n   * Replace existing certificate (convenience method)\n   * Uploads a new certificate, replacing the existing one\n   *\n   * @param companyId - Company ID\n   * @param certificateData - New certificate data\n   * @returns Upload result\n   * @throws {ValidationError} If certificate is invalid\n   * @throws {NotFoundError} If company doesn't exist\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.companies.replaceCertificate('company-123', {\n   *   file: newCertificateBuffer,\n   *   password: 'new-password',\n   *   filename: 'new-certificate.pfx'\n   * });\n   * ```\n   */\n  async replaceCertificate(\n    companyId: string,\n    certificateData: {\n      file: any;\n      password: string;\n      filename?: string;\n    }\n  ): Promise<{ uploaded: boolean; message?: string }> {\n    // Same as uploadCertificate - API handles replacement\n    return await this.uploadCertificate(companyId, certificateData);\n  }\n\n  /**\n   * Check if certificate is expiring soon for a company\n   *\n   * @param companyId - Company ID\n   * @param thresholdDays - Days threshold (default: 30)\n   * @returns Warning object if expiring soon, null otherwise\n   * @throws {NotFoundError} If company doesn't exist\n   *\n   * @example\n   * ```typescript\n   * const warning = await nfe.companies.checkCertificateExpiration('company-123', 30);\n   *\n   * if (warning) {\n   *   console.warn(`Certificate expiring in ${warning.daysRemaining} days!`);\n   *   console.log('Expiration date:', warning.expiresOn);\n   * }\n   * ```\n   */\n  async checkCertificateExpiration(\n    companyId: string,\n    thresholdDays: number = 30\n  ): Promise<{\n    isExpiring: true;\n    daysRemaining: number;\n    expiresOn: Date;\n  } | null> {\n    const status = await this.getCertificateStatus(companyId);\n\n    if (!status.hasCertificate || !status.expiresOn) {\n      return null;\n    }\n\n    const expirationDate = new Date(status.expiresOn);\n    const daysRemaining = CertificateValidator.getDaysUntilExpiration(expirationDate);\n\n    // Check if expiring within threshold\n    if (daysRemaining >= 0 && daysRemaining < thresholdDays) {\n      return {\n        isExpiring: true,\n        daysRemaining,\n        expiresOn: expirationDate\n      };\n    }\n\n    return null;\n  }\n\n  // --------------------------------------------------------------------------\n  // Search & Helper Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Find company by federal tax number (CNPJ or CPF)\n   *\n   * @param taxNumber - Federal tax number (11 digits for CPF, 14 for CNPJ)\n   * @returns Company if found, null otherwise\n   *\n   * @example\n   * ```typescript\n   * const company = await nfe.companies.findByTaxNumber(12345678901234);\n   *\n   * if (company) {\n   *   console.log('Found:', company.name);\n   * } else {\n   *   console.log('Company not found');\n   * }\n   * ```\n   */\n  async findByTaxNumber(taxNumber: number): Promise<Company | null> {\n    // Validate tax number format\n    const length = taxNumber.toString().length;\n    if (length !== 11 && length !== 14) {\n      throw new ValidationError('Tax number must be 11 digits (CPF) or 14 digits (CNPJ)');\n    }\n\n    const companies = await this.listAll();\n\n    const found = companies.find((company: Company) =>\n      company.federalTaxNumber === taxNumber\n    );\n\n    return found || null;\n  }\n\n  /**\n   * Find company by name (case-insensitive partial match)\n   *\n   * @param name - Company name or part of it\n   * @returns Array of matching companies\n   *\n   * @example\n   * ```typescript\n   * const companies = await nfe.companies.findByName('Acme');\n   *\n   * companies.forEach(company => {\n   *   console.log('Match:', company.name);\n   * });\n   * ```\n   */\n  async findByName(name: string): Promise<Company[]> {\n    if (!name || name.trim().length === 0) {\n      throw new ValidationError('Search name cannot be empty');\n    }\n\n    const companies = await this.listAll();\n    const searchTerm = name.toLowerCase().trim();\n\n    return companies.filter((company: Company) =>\n      company.name?.toLowerCase().includes(searchTerm)\n    );\n  }\n\n  /**\n   * Get companies with active certificates\n   *\n   * @returns Array of companies that have valid certificates\n   *\n   * @example\n   * ```typescript\n   * const companiesWithCerts = await nfe.companies.getCompaniesWithCertificates();\n   *\n   * console.log(`Found ${companiesWithCerts.length} companies with certificates`);\n   * ```\n   */\n  async getCompaniesWithCertificates(): Promise<Company[]> {\n    const companies = await this.listAll();\n\n    // Sem requisição por empresa: `GET /v1/companies` já devolve `certificate` em\n    // cada item. A versão anterior chamava getCertificateStatus() em série sobre a\n    // conta inteira — numa conta com centenas de empresas, centenas de idas à rede\n    // por chamada.\n    return companies.filter(company => readListedCertificate(company)?.status === 'Active');\n  }\n\n  /**\n   * Get companies with expiring certificates\n   *\n   * @param thresholdDays - Days threshold (default: 30)\n   * @returns Array of companies with expiring certificates\n   *\n   * @example\n   * ```typescript\n   * const expiring = await nfe.companies.getCompaniesWithExpiringCertificates(30);\n   *\n   * expiring.forEach(company => {\n   *   console.log(`${company.name} certificate expiring soon`);\n   * });\n   * ```\n   */\n  async getCompaniesWithExpiringCertificates(thresholdDays: number = 30): Promise<Company[]> {\n    const companies = await this.listAll();\n\n    // Mesmo motivo de getCompaniesWithCertificates: o vencimento já vem na listagem,\n    // no campo `expiresOn` do certificado embutido.\n    return companies.filter(company => {\n      const expiresOn = readListedCertificate(company)?.expiresOn;\n      if (!expiresOn) return false;\n\n      const daysRemaining = CertificateValidator.getDaysUntilExpiration(new Date(expiresOn));\n      return daysRemaining >= 0 && daysRemaining < thresholdDays;\n    });\n  }\n\n  // --------------------------------------------------------------------------\n  // Private Helper Methods\n  // --------------------------------------------------------------------------\n\n  private createFormData(): any {\n    if (typeof FormData !== 'undefined') {\n      return new FormData();\n    } else {\n      // Fallback for environments without FormData\n      throw new Error('FormData is not available in this environment');\n    }\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\nexport function createCompaniesResource(http: HttpClient): CompaniesResource {\n  return new CompaniesResource(http);\n}\n","/**\n * LegalPeople Resource\n * Manages legal entities (pessoas jurídicas) scoped by company\n *\n * ## Restrição de formato do `company_id`\n *\n * Estas rotas aceitam **somente** `company_id` no formato `ObjectId` de 24\n * hexadecimais. Empresa cujo id tem 32 caracteres recebe\n * `400 \"company id is not valid\"` em toda chamada — a rota valida o id como\n * `ObjectId` antes de qualquer coisa.\n *\n * É **limite do servidor**, não do SDK: não há conversão possível entre os dois\n * formatos, e validar localmente só antecipa a mesma recusa com mensagem pior.\n * Medido em 2026-09-02 sobre 50 empresas da mesma conta:\n *\n *   30 empresas com id de 24 hex   -> 200\n *   19 empresas com id de 32 chars -> 400 \"company id is not valid\"\n *\n * Um id de 24 hex sintético (inexistente) responde `404 \"Company not found.\"`,\n * ou seja: o validador de formato passa e a busca é que falha. Empresas criadas\n * depois da mudança de formato de id ficaram inalcançáveis por estas rotas.\n * Pendência aberta com o time de API.\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type { LegalPerson, ResourceId, ListResponse } from '../types.js';\n\n/**\n * LegalPeople resource for managing legal entities (pessoas jurídicas)\n * All operations are scoped by company_id\n */\nexport class LegalPeopleResource {\n  constructor(private readonly http: HttpClient) {}\n\n  /**\n   * List all legal people for a company\n   *\n   * @param companyId - Company ID\n   * @returns List of legal people\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.legalPeople.list('company-id');\n   * console.log(`Found ${result.legalPeople?.length ?? 0} legal entities`);\n   * ```\n   */\n  async list(companyId: ResourceId): Promise<ListResponse<LegalPerson>> {\n    const path = `/companies/${companyId}/legalpeople`;\n    const response = await this.http.get<{ legalPeople: LegalPerson[] }>(path);\n\n    // API returns: { legalPeople: [...] }\n    // Transform to our standard ListResponse format\n    return {\n      data: response.data.legalPeople || []\n    };\n  }\n\n  /**\n   * Create a new legal person\n   *\n   * @param companyId - Company ID\n   * @param data - Legal person data\n   * @returns Created legal person\n   *\n   * @example\n   * ```typescript\n   * const legalPerson = await nfe.legalPeople.create('company-id', {\n   *   federalTaxNumber: '12345678901234',\n   *   name: 'Empresa Exemplo Ltda',\n   *   email: 'contato@empresa.com.br',\n   *   address: {\n   *     street: 'Av. Paulista, 1000',\n   *     neighborhood: 'Bela Vista',\n   *     city: { code: '3550308', name: 'São Paulo' },\n   *     state: 'SP',\n   *     postalCode: '01310-100'\n   *     }\n   * });\n   * ```\n   */\n  async create(\n    companyId: ResourceId,\n    data: Partial<LegalPerson>\n  ): Promise<LegalPerson> {\n    const path = `/companies/${companyId}/legalpeople`;\n    const response = await this.http.post<{ legalPeople: LegalPerson }>(path, data);\n\n    // API returns wrapped object: { legalPeople: {...} }\n    return response.data.legalPeople;\n  }\n\n  /**\n   * Retrieve a specific legal person\n   *\n   * @param companyId - Company ID\n   * @param legalPersonId - Legal person ID\n   * @returns Legal person details\n   *\n   * @example\n   * ```typescript\n   * const legalPerson = await nfe.legalPeople.retrieve(\n   *   'company-id',\n   *   'legal-person-id'\n   * );\n   * console.log(legalPerson.name);\n   * ```\n   */\n  async retrieve(\n    companyId: ResourceId,\n    legalPersonId: ResourceId\n  ): Promise<LegalPerson> {\n    const path = `/companies/${companyId}/legalpeople/${legalPersonId}`;\n    const response = await this.http.get<{ legalPeople: LegalPerson }>(path);\n\n    // API returns wrapped object: { legalPeople: {...} }\n    return response.data.legalPeople;\n  }\n\n  /**\n   * Update a legal person\n   *\n   * @param companyId - Company ID\n   * @param legalPersonId - Legal person ID\n   * @param data - Data to update\n   * @returns Updated legal person\n   *\n   * @example\n   * ```typescript\n   * const updated = await nfe.legalPeople.update(\n   *   'company-id',\n   *   'legal-person-id',\n   *   { email: 'novo@email.com' }\n   * );\n   * ```\n   */\n  async update(\n    companyId: ResourceId,\n    legalPersonId: ResourceId,\n    data: Partial<LegalPerson>\n  ): Promise<LegalPerson> {\n    const path = `/companies/${companyId}/legalpeople/${legalPersonId}`;\n    const response = await this.http.put<{ legalPeople: LegalPerson }>(path, data);\n\n    // API returns wrapped object: { legalPeople: {...} }\n    return response.data.legalPeople;\n  }\n\n  /**\n   * Delete a legal person\n   *\n   * @param companyId - Company ID\n   * @param legalPersonId - Legal person ID\n   *\n   * @example\n   * ```typescript\n   * await nfe.legalPeople.delete('company-id', 'legal-person-id');\n   * ```\n   */\n  async delete(\n    companyId: ResourceId,\n    legalPersonId: ResourceId\n  ): Promise<void> {\n    const path = `/companies/${companyId}/legalpeople/${legalPersonId}`;\n    await this.http.delete(path);\n  }\n\n  /**\n   * Create multiple legal people in batch\n   *\n   * @param companyId - Company ID\n   * @param data - Array of legal people data\n   * @returns Array of created legal people\n   *\n   * @example\n   * ```typescript\n   * const created = await nfe.legalPeople.createBatch('company-id', [\n   *   { name: 'Empresa 1', federalTaxNumber: '11111111111111', ... },\n   *   { name: 'Empresa 2', federalTaxNumber: '22222222222222', ... }\n   * ]);\n   * ```\n   */\n  async createBatch(\n    companyId: ResourceId,\n    data: Array<Partial<LegalPerson>>\n  ): Promise<LegalPerson[]> {\n    const promises = data.map(person => this.create(companyId, person));\n    return Promise.all(promises);\n  }\n\n  /**\n   * Find legal person by federal tax number (CNPJ)\n   *\n   * @param companyId - Company ID\n   * @param federalTaxNumber - CNPJ (only numbers)\n   * @returns Legal person or undefined if not found\n   *\n   * @example\n   * ```typescript\n   * const person = await nfe.legalPeople.findByTaxNumber(\n   *   'company-id',\n   *   '12345678901234'\n   * );\n   * if (person) {\n   *   console.log('Found:', person.name);\n   * }\n   * ```\n   */\n  async findByTaxNumber(\n    companyId: ResourceId,\n    federalTaxNumber: string\n  ): Promise<LegalPerson | undefined> {\n    const result = await this.list(companyId);\n    const people = (result.data ?? []) as LegalPerson[];\n\n    return people.find(\n      (person: LegalPerson) =>\n        person.federalTaxNumber?.toString() === federalTaxNumber\n    );\n  }\n}\n","/**\n * NaturalPeople Resource\n * Manages natural persons (pessoas físicas) scoped by company\n *\n * ## Restrição de formato do `company_id`\n *\n * Estas rotas aceitam **somente** `company_id` no formato `ObjectId` de 24\n * hexadecimais. Empresa cujo id tem 32 caracteres recebe\n * `400 \"company id is not valid\"` em toda chamada — a rota valida o id como\n * `ObjectId` antes de qualquer coisa.\n *\n * É **limite do servidor**, não do SDK: não há conversão possível entre os dois\n * formatos, e validar localmente só antecipa a mesma recusa com mensagem pior.\n * Medido em 2026-09-02 sobre 50 empresas da mesma conta:\n *\n *   30 empresas com id de 24 hex   -> 200\n *   19 empresas com id de 32 chars -> 400 \"company id is not valid\"\n *\n * Um id de 24 hex sintético (inexistente) responde `404 \"Company not found.\"`,\n * ou seja: o validador de formato passa e a busca é que falha. Empresas criadas\n * depois da mudança de formato de id ficaram inalcançáveis por estas rotas.\n * Pendência aberta com o time de API.\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type { NaturalPerson, ResourceId, ListResponse } from '../types.js';\n\n/**\n * NaturalPeople resource for managing natural persons (pessoas físicas)\n * All operations are scoped by company_id\n */\nexport class NaturalPeopleResource {\n  constructor(private readonly http: HttpClient) {}\n\n  /**\n   * List all natural people for a company\n   *\n   * @param companyId - Company ID\n   * @returns List of natural people\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.naturalPeople.list('company-id');\n   * console.log(`Found ${result.data.length} natural persons`);\n   * ```\n   */\n  async list(companyId: ResourceId): Promise<ListResponse<NaturalPerson>> {\n    const path = `/companies/${companyId}/naturalpeople`;\n    const response = await this.http.get<{ naturalPeople: NaturalPerson[] }>(path);\n\n    // API returns: { naturalPeople: [...] }\n    // Transform to our standard ListResponse format\n    return {\n      data: response.data.naturalPeople || []\n    };\n  }\n\n  /**\n   * Create a new natural person\n   *\n   * @param companyId - Company ID\n   * @param data - Natural person data\n   * @returns Created natural person\n   *\n   * @example\n   * ```typescript\n   * const naturalPerson = await nfe.naturalPeople.create('company-id', {\n   *   federalTaxNumber: '12345678901',\n   *   name: 'João Silva',\n   *   email: 'joao@exemplo.com',\n   *   address: {\n   *     street: 'Rua Exemplo, 123',\n   *     neighborhood: 'Centro',\n   *     city: { code: '3550308', name: 'São Paulo' },\n   *     state: 'SP',\n   *     postalCode: '01000-000'\n   *   }\n   * });\n   * ```\n   */\n  async create(\n    companyId: ResourceId,\n    data: Partial<NaturalPerson>\n  ): Promise<NaturalPerson> {\n    const path = `/companies/${companyId}/naturalpeople`;\n    const response = await this.http.post<{ naturalPeople: NaturalPerson }>(path, data);\n\n    // API returns wrapped object: { naturalPeople: {...} }\n    return response.data.naturalPeople;\n  }\n\n  /**\n   * Retrieve a specific natural person\n   *\n   * @param companyId - Company ID\n   * @param naturalPersonId - Natural person ID\n   * @returns Natural person details\n   *\n   * @example\n   * ```typescript\n   * const naturalPerson = await nfe.naturalPeople.retrieve(\n   *   'company-id',\n   *   'natural-person-id'\n   * );\n   * console.log(naturalPerson.name);\n   * ```\n   */\n  async retrieve(\n    companyId: ResourceId,\n    naturalPersonId: ResourceId\n  ): Promise<NaturalPerson> {\n    const path = `/companies/${companyId}/naturalpeople/${naturalPersonId}`;\n    const response = await this.http.get<{ naturalPeople: NaturalPerson }>(path);\n\n    // API returns wrapped object: { naturalPeople: {...} }\n    return response.data.naturalPeople;\n  }\n\n  /**\n   * Update a natural person\n   *\n   * @param companyId - Company ID\n   * @param naturalPersonId - Natural person ID\n   * @param data - Data to update\n   * @returns Updated natural person\n   *\n   * @example\n   * ```typescript\n   * const updated = await nfe.naturalPeople.update(\n   *   'company-id',\n   *   'natural-person-id',\n   *   { email: 'novo@email.com' }\n   * );\n   * ```\n   */\n  async update(\n    companyId: ResourceId,\n    naturalPersonId: ResourceId,\n    data: Partial<NaturalPerson>\n  ): Promise<NaturalPerson> {\n    const path = `/companies/${companyId}/naturalpeople/${naturalPersonId}`;\n    const response = await this.http.put<{ naturalPeople: NaturalPerson }>(path, data);\n\n    // API returns wrapped object: { naturalPeople: {...} }\n    return response.data.naturalPeople;\n  }\n\n  /**\n   * Delete a natural person\n   *\n   * @param companyId - Company ID\n   * @param naturalPersonId - Natural person ID\n   *\n   * @example\n   * ```typescript\n   * await nfe.naturalPeople.delete('company-id', 'natural-person-id');\n   * ```\n   */\n  async delete(\n    companyId: ResourceId,\n    naturalPersonId: ResourceId\n  ): Promise<void> {\n    const path = `/companies/${companyId}/naturalpeople/${naturalPersonId}`;\n    await this.http.delete(path);\n  }\n\n  /**\n   * Create multiple natural people in batch\n   *\n   * @param companyId - Company ID\n   * @param data - Array of natural people data\n   * @returns Array of created natural people\n   *\n   * @example\n   * ```typescript\n   * const created = await nfe.naturalPeople.createBatch('company-id', [\n   *   { name: 'João Silva', federalTaxNumber: '11111111111', ... },\n   *   { name: 'Maria Santos', federalTaxNumber: '22222222222', ... }\n   * ]);\n   * ```\n   */\n  async createBatch(\n    companyId: ResourceId,\n    data: Array<Partial<NaturalPerson>>\n  ): Promise<NaturalPerson[]> {\n    const promises = data.map(person => this.create(companyId, person));\n    return Promise.all(promises);\n  }\n\n  /**\n   * Find natural person by federal tax number (CPF)\n   *\n   * @param companyId - Company ID\n   * @param federalTaxNumber - CPF (only numbers)\n   * @returns Natural person or undefined if not found\n   *\n   * @example\n   * ```typescript\n   * const person = await nfe.naturalPeople.findByTaxNumber(\n   *   'company-id',\n   *   '12345678901'\n   * );\n   * if (person) {\n   *   console.log('Found:', person.name);\n   * }\n   * ```\n   */\n  async findByTaxNumber(\n    companyId: ResourceId,\n    federalTaxNumber: string\n  ): Promise<NaturalPerson | undefined> {\n    const result = await this.list(companyId);\n    const people = (result.data ?? []) as NaturalPerson[];\n\n    return people.find(\n      (person: NaturalPerson) =>\n        person.federalTaxNumber?.toString() === federalTaxNumber\n    );\n  }\n}\n","/**\n * Webhooks Resource\n * Manages webhook subscriptions for event notifications\n */\n\nimport { createHmac, timingSafeEqual } from 'node:crypto';\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  AccountWebhook,\n  Webhook,\n  WebhookEvent,\n  WebhookEventType,\n  ListResponse,\n  ResourceId,\n} from '../types.js';\n\n/**\n * Webhooks resource for managing event subscriptions.\n *\n * Webhooks are managed at the **account** level (`/v2/webhooks`) — use the\n * `*AccountWebhook*` methods. The company-scoped methods (`list`, `create`,\n * `retrieve`, `update`, `delete`, `test`) are deprecated: the route\n * `/v1/companies/{id}/webhooks` returns 404 on the current API (confirmed on\n * two accounts, 2026-07-02).\n */\nexport class WebhooksResource {\n  /**\n   * HTTP client for ACCOUNT-scoped endpoints (host-root `/v2/webhooks`). When not\n   * provided, falls back to the company-scoped client (back-compat for tests).\n   */\n  private readonly account: HttpClient;\n\n  constructor(\n    private readonly http: HttpClient,\n    accountHttp?: HttpClient\n  ) {\n    this.account = accountHttp ?? http;\n  }\n\n  /**\n   * List all webhooks for a company\n   *\n   * @deprecated A rota `/v1/companies/{id}/webhooks` retorna 404 na API atual\n   * (confirmado em duas contas, 2026-07-02). Use {@link listAccountWebhooks}.\n   *\n   * @param companyId - Company ID\n   * @returns List of webhooks\n   * \n   * @example\n   * ```typescript\n   * const result = await nfe.webhooks.list('company-id');\n   * console.log(`You have ${result.data.length} webhooks configured`);\n   * ```\n   */\n  async list(companyId: ResourceId): Promise<ListResponse<Webhook>> {\n    const path = `/companies/${companyId}/webhooks`;\n    const response = await this.http.get<ListResponse<Webhook>>(path);\n    \n    return response.data;\n  }\n\n  /**\n   * Create a new webhook subscription\n   *\n   * @deprecated A rota `/v1/companies/{id}/webhooks` retorna 404 na API atual\n   * (confirmado em duas contas, 2026-07-02). Use {@link createAccountWebhook}.\n   *\n   * @param companyId - Company ID\n   * @param data - Webhook configuration\n   * @returns Created webhook\n   * \n   * @example\n   * ```typescript\n   * const webhook = await nfe.webhooks.create('company-id', {\n   *   url: 'https://seu-site.com/webhook/nfe',\n   *   events: ['invoice.issued', 'invoice.cancelled'],\n   *   secret: 'sua-chave-secreta-opcional'\n   * });\n   * ```\n   */\n  async create(\n    companyId: ResourceId,\n    data: Partial<Webhook>\n  ): Promise<Webhook> {\n    const path = `/companies/${companyId}/webhooks`;\n    const response = await this.http.post<Webhook>(path, data);\n    \n    return response.data;\n  }\n\n  /**\n   * Retrieve a specific webhook\n   *\n   * @deprecated A rota `/v1/companies/{id}/webhooks` retorna 404 na API atual\n   * (confirmado em duas contas, 2026-07-02). Use {@link retrieveAccountWebhook}.\n   *\n   * @param companyId - Company ID\n   * @param webhookId - Webhook ID\n   * @returns Webhook details\n   * \n   * @example\n   * ```typescript\n   * const webhook = await nfe.webhooks.retrieve('company-id', 'webhook-id');\n   * console.log('Webhook URL:', webhook.url);\n   * ```\n   */\n  async retrieve(\n    companyId: ResourceId,\n    webhookId: ResourceId\n  ): Promise<Webhook> {\n    const path = `/companies/${companyId}/webhooks/${webhookId}`;\n    const response = await this.http.get<Webhook>(path);\n    \n    return response.data;\n  }\n\n  /**\n   * Update a webhook\n   *\n   * @deprecated A rota `/v1/companies/{id}/webhooks` retorna 404 na API atual\n   * (confirmado em duas contas, 2026-07-02). Use {@link updateAccountWebhook}.\n   *\n   * @param companyId - Company ID\n   * @param webhookId - Webhook ID\n   * @param data - Data to update\n   * @returns Updated webhook\n   * \n   * @example\n   * ```typescript\n   * const updated = await nfe.webhooks.update(\n   *   'company-id',\n   *   'webhook-id',\n   *   { events: ['invoice.issued', 'invoice.cancelled', 'invoice.failed'] }\n   * );\n   * ```\n   */\n  async update(\n    companyId: ResourceId,\n    webhookId: ResourceId,\n    data: Partial<Webhook>\n  ): Promise<Webhook> {\n    const path = `/companies/${companyId}/webhooks/${webhookId}`;\n    const response = await this.http.put<Webhook>(path, data);\n    \n    return response.data;\n  }\n\n  /**\n   * Delete a webhook\n   *\n   * @deprecated A rota `/v1/companies/{id}/webhooks` retorna 404 na API atual\n   * (confirmado em duas contas, 2026-07-02). Use {@link deleteAccountWebhook}.\n   *\n   * @param companyId - Company ID\n   * @param webhookId - Webhook ID\n   * \n   * @example\n   * ```typescript\n   * await nfe.webhooks.delete('company-id', 'webhook-id');\n   * console.log('Webhook deleted');\n   * ```\n   */\n  async delete(\n    companyId: ResourceId,\n    webhookId: ResourceId\n  ): Promise<void> {\n    const path = `/companies/${companyId}/webhooks/${webhookId}`;\n    await this.http.delete(path);\n  }\n\n  /**\n   * Validate a webhook signature sent by NFE.io.\n   *\n   * NFE.io signs every webhook delivery with `HMAC-SHA1(secret, raw_body_bytes)`,\n   * encoded as hex (uppercase in the wire format, but compared case-insensitively),\n   * and prefixed with `sha1=`. The signed value is delivered in the\n   * `X-Hub-Signature` HTTP header.\n   *\n   * @param payload - The raw request body. Pass a `Buffer` whenever possible to\n   *                  preserve byte-exact content. Strings are encoded as UTF-8.\n   *                  Re-serializing JSON (e.g. `JSON.stringify(req.body)`) does\n   *                  NOT work because property order and whitespace will differ\n   *                  from the bytes NFE.io signed.\n   * @param signature - The full value of the `X-Hub-Signature` header, including\n   *                    the `sha1=` prefix. Accepts `string` or `string[]` (the\n   *                    shape Node's `IncomingMessage` exposes for repeated\n   *                    headers); `undefined`/`null` are treated as invalid.\n   * @param secret - The webhook secret configured when the webhook was created.\n   * @returns `true` only when the signature matches; `false` for any mismatch,\n   *          malformed input, missing input, or wrong algorithm prefix. This\n   *          method never throws.\n   *\n   * @example\n   * ```typescript\n   * import express from 'express';\n   *\n   * // IMPORTANT: capture the raw body BEFORE any JSON parser so that\n   * // validateSignature sees the exact bytes NFE.io signed.\n   * app.post(\n   *   '/webhook/nfe',\n   *   express.raw({ type: '*\\/*' }),\n   *   (req, res) => {\n   *     const ok = nfe.webhooks.validateSignature(\n   *       req.body,                              // Buffer with exact bytes\n   *       req.headers['x-hub-signature'],        // correct header\n   *       process.env.NFE_WEBHOOK_SECRET ?? ''\n   *     );\n   *     if (!ok) return res.status(401).end();\n   *\n   *     const event = JSON.parse(req.body.toString('utf8'));\n   *     // process event...\n   *     res.status(204).end();\n   *   }\n   * );\n   * ```\n   */\n  validateSignature(\n    payload: Buffer | string,\n    signature: string | string[] | undefined,\n    secret: string\n  ): boolean {\n    if (!secret || signature == null) return false;\n\n    const sigStr = Array.isArray(signature) ? signature[0] : signature;\n    if (typeof sigStr !== 'string' || sigStr.length === 0) return false;\n\n    const PREFIX = 'sha1=';\n    if (sigStr.length <= PREFIX.length) return false;\n    if (sigStr.slice(0, PREFIX.length).toLowerCase() !== PREFIX) return false;\n\n    // HMAC-SHA1 hex is always 40 chars. Validate shape before decoding so we\n    // never feed garbage into Buffer.from(hex) (which silently returns shorter\n    // buffers on invalid input).\n    const received = sigStr.slice(PREFIX.length).toLowerCase();\n    if (!/^[a-f0-9]{40}$/.test(received)) return false;\n\n    const body = Buffer.isBuffer(payload) ? payload : Buffer.from(payload, 'utf8');\n    const expected = createHmac('sha1', secret).update(body).digest('hex');\n\n    // Both decode to exactly 20 bytes (guaranteed: received passed the\n    // /^[a-f0-9]{40}$/ check above; expected is HMAC-SHA1 hex). That's why\n    // timingSafeEqual is safe to call here without a length pre-check.\n    return timingSafeEqual(Buffer.from(received, 'hex'), Buffer.from(expected, 'hex'));\n  }\n\n  /**\n   * Test webhook delivery\n   *\n   * Sends a test event to the webhook URL to verify it's working\n   *\n   * @deprecated A rota `/v1/companies/{id}/webhooks` retorna 404 na API atual\n   * (confirmado em duas contas, 2026-07-02). Use {@link pingAccountWebhook}.\n   *\n   * @param companyId - Company ID\n   * @param webhookId - Webhook ID\n   * @returns Test result\n   * \n   * @example\n   * ```typescript\n   * const result = await nfe.webhooks.test('company-id', 'webhook-id');\n   * if (result.success) {\n   *   console.log('Webhook is working!');\n   * }\n   * ```\n   */\n  async test(\n    companyId: ResourceId,\n    webhookId: ResourceId\n  ): Promise<{ success: boolean; message?: string }> {\n    const path = `/companies/${companyId}/webhooks/${webhookId}/test`;\n    const response = await this.http.post<{ success: boolean; message?: string }>(\n      path,\n      {}\n    );\n    \n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Account-scoped operations (/v2/webhooks) — NOT company-scoped.\n  // These take no companyId; they manage webhooks at the account level.\n  //\n  // Wire contract (specs oficiais + confirmado ao vivo em 2026-07-02):\n  //  - create/update REQUESTS must be wrapped in a `webHook` envelope — the API\n  //    rejects a bare body with 400 \"missing required properties: 'webHook'\".\n  //  - Single-object RESPONSES come wrapped as { webHook: {...} } and are\n  //    unwrapped here (with a defensive raw-body fallback).\n  // --------------------------------------------------------------------------\n\n  /**\n   * List account-level webhooks (`GET /v2/webhooks`).\n   *\n   * The API wraps the result as `{ webHooks: [...] }`; this normalizes it to the\n   * SDK's `ListResponse<AccountWebhook>` (`{ data: [...] }`).\n   */\n  async listAccountWebhooks(): Promise<ListResponse<AccountWebhook>> {\n    const response = await this.account.get<{ webHooks?: AccountWebhook[] }>('/webhooks');\n    return { data: response.data?.webHooks ?? [] };\n  }\n\n  /**\n   * Create an account-level webhook (`POST /v2/webhooks`).\n   *\n   * NFE.io **verifies the target URI at creation time**: it sends a test request\n   * (ping) to `data.uri` and the endpoint must already be live and answer 2xx,\n   * otherwise creation fails. The `secret` must be 32–64 characters; it is echoed\n   * back in the create response but omitted on subsequent reads.\n   *\n   * @example\n   * ```typescript\n   * const webhook = await nfe.webhooks.createAccountWebhook({\n   *   uri: 'https://seu-site.com/webhook/nfe', // precisa responder 2xx já na criação\n   *   contentType: 'json',\n   *   secret: 'um-segredo-de-32-a-64-caracteres-aqui',\n   *   filters: ['service_invoice.issued_successfully', 'service_invoice.cancelled_successfully'],\n   * });\n   * console.log('Webhook criado:', webhook.id);\n   * ```\n   */\n  async createAccountWebhook(data: AccountWebhook): Promise<AccountWebhook> {\n    const response = await this.account.post<{ webHook?: AccountWebhook }>('/webhooks', {\n      webHook: data,\n    });\n    return response.data?.webHook ?? (response.data as AccountWebhook);\n  }\n\n  /** Retrieve an account-level webhook by id (`GET /v2/webhooks/{id}`). */\n  async retrieveAccountWebhook(webhookId: ResourceId): Promise<AccountWebhook> {\n    const response = await this.account.get<{ webHook?: AccountWebhook }>(\n      `/webhooks/${webhookId}`\n    );\n    return response.data?.webHook ?? (response.data as AccountWebhook);\n  }\n\n  /**\n   * Update an account-level webhook by id (`PUT /v2/webhooks/{id}`).\n   *\n   * ⚠️ O `PUT` tem **semântica de substituição integral** (confirmado ao vivo em\n   * 2026-07-03): campos omitidos voltam ao padrão — em particular, um update sem\n   * `status` **desativa o webhook** (`status` volta a `\"Inactive\"`). Envie o\n   * objeto completo, por exemplo partindo de {@link retrieveAccountWebhook}:\n   *\n   * @example\n   * ```typescript\n   * const current = await nfe.webhooks.retrieveAccountWebhook(id);\n   * await nfe.webhooks.updateAccountWebhook(id, {\n   *   ...current,\n   *   filters: [...(current.filters ?? []), 'service_invoice.cancelled_successfully'],\n   * });\n   * ```\n   */\n  async updateAccountWebhook(\n    webhookId: ResourceId,\n    data: Partial<AccountWebhook>\n  ): Promise<AccountWebhook> {\n    const response = await this.account.put<{ webHook?: AccountWebhook }>(\n      `/webhooks/${webhookId}`,\n      { webHook: data }\n    );\n    return response.data?.webHook ?? (response.data as AccountWebhook);\n  }\n\n  /** Delete a single account-level webhook by id (`DELETE /v2/webhooks/{id}`). */\n  async deleteAccountWebhook(webhookId: ResourceId): Promise<void> {\n    await this.account.delete(`/webhooks/${webhookId}`);\n  }\n\n  /**\n   * ⚠️ DANGEROUS: delete **ALL** account-level webhooks (`DELETE /v2/webhooks`).\n   *\n   * Named distinctly from {@link deleteAccountWebhook} so it can never be reached\n   * by a mistyped single delete. This removes every webhook on the account.\n   */\n  async deleteAllAccountWebhooks(): Promise<void> {\n    await this.account.delete('/webhooks');\n  }\n\n  /** Trigger a test ping for an account-level webhook (`PUT /v2/webhooks/{id}/pings`). */\n  async pingAccountWebhook(webhookId: ResourceId): Promise<void> {\n    await this.account.put(`/webhooks/${webhookId}/pings`, {});\n  }\n\n  /**\n   * Fetch the live list of available webhook event types (`GET /v2/webhooks/eventTypes`).\n   *\n   * Prefer this over {@link getAvailableEvents}: the server is the source of truth,\n   * so new event types are picked up automatically. The return is the **open** union\n   * {@link WebhookEventType}, so new server-side events don't break typing.\n   * The API wraps the result as `{ eventTypes: [{ id, ... }] }`; this extracts the ids.\n   */\n  async fetchEventTypes(): Promise<WebhookEventType[]> {\n    const response = await this.account.get<{ eventTypes?: Array<{ id: string }> }>(\n      '/webhooks/eventTypes'\n    );\n    return (response.data?.eventTypes ?? []).map((e) => e.id);\n  }\n\n  /**\n   * Get available webhook events.\n   *\n   * @deprecated This returns a hardcoded list that can drift from the platform's\n   * real event set. Use {@link fetchEventTypes} to get the live list from the API.\n   *\n   * @returns List of available events\n   */\n  getAvailableEvents(): WebhookEvent[] {\n    return [\n      'invoice.issued',\n      'invoice.cancelled',\n      'invoice.failed',\n      'invoice.processing',\n      'company.created',\n      'company.updated',\n      'company.deleted',\n    ] as WebhookEvent[];\n  }\n}\n","/**\n * NFE.io SDK v3 - Addresses Resource\n *\n * Handles address lookup operations via the Address API\n * Uses a separate API host: address.api.nfe.io\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type { Address, AddressLookupResponse } from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Base URL for Address API */\nexport const ADDRESS_API_BASE_URL = 'https://address.api.nfe.io/v2';\n\n/** Regex pattern for valid postal code (CEP) */\nconst POSTAL_CODE_PATTERN = /^\\d{5}-?\\d{3}$/;\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Validates postal code format (CEP)\n * Accepts formats: 01310100 or 01310-100\n */\nfunction validatePostalCode(postalCode: string): void {\n  if (!postalCode || postalCode.trim() === '') {\n    throw new ValidationError('Postal code is required');\n  }\n\n  const normalized = postalCode.trim();\n  if (!POSTAL_CODE_PATTERN.test(normalized)) {\n    throw new ValidationError(\n      `Invalid postal code format: \"${postalCode}\". Expected 8 digits (e.g., \"01310100\" or \"01310-100\").`\n    );\n  }\n}\n\n/**\n * Normalizes postal code by removing hyphen and trimming whitespace\n */\nfunction normalizePostalCode(postalCode: string): string {\n  return postalCode.trim().replace(/-/g, '');\n}\n\n// ============================================================================\n// Addresses Resource\n// ============================================================================\n\n/**\n * Addresses API Resource\n *\n * @description\n * Provides operations for looking up Brazilian addresses using the NFE.io Address API.\n * Data is sourced from Correios DNE (Diretório Nacional de Endereços) integrated with IBGE city codes.\n *\n * **Note:** This resource uses a different API host (address.api.nfe.io) and may require\n * a separate API key configured via `dataApiKey` in the client configuration.\n *\n * The live `address.api.nfe.io/v2` API supports **postal code lookup only**. A single\n * address is returned for a given CEP; there is no working address search/free-text\n * endpoint on this host (see the `fix-address-lookup-api-mismatch` change).\n *\n * @example Basic postal code lookup\n * ```typescript\n * const address = await nfe.addresses.lookupByPostalCode('01310-100');\n * console.log(address.street); // 'Paulista'\n * console.log(`${address.streetSuffix} ${address.street}, ${address.city.name}/${address.state}`);\n * ```\n */\nexport class AddressesResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Public Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Lookup address by postal code (CEP)\n   *\n   * Calls `GET /v2/addresses/{cep}` and returns the single {@link Address} carried in\n   * the API's `{ address }` envelope.\n   *\n   * @param postalCode - Brazilian postal code (CEP), with or without hyphen\n   * @returns Promise resolving to the matching {@link Address}\n   * @throws {ValidationError} If postal code format is invalid\n   * @throws {NotFoundError} If no address found for the postal code\n   *\n   * @example\n   * ```typescript\n   * // With or without hyphen — both normalize to the 8-digit form\n   * const address = await nfe.addresses.lookupByPostalCode('01310-100');\n   *\n   * console.log(`${address.streetSuffix} ${address.street}, ${address.city.name} - ${address.state}`);\n   * console.log(address.postalCode); // '01310-100' (API returns it formatted)\n   * ```\n   */\n  async lookupByPostalCode(postalCode: string): Promise<Address> {\n    validatePostalCode(postalCode);\n\n    const normalizedCode = normalizePostalCode(postalCode);\n    const response = await this.http.get<AddressLookupResponse>(\n      `/addresses/${normalizedCode}`\n    );\n\n    return response.data.address;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Creates an AddressesResource instance\n *\n * @param http - HTTP client configured for the Address API\n * @returns AddressesResource instance\n */\nexport function createAddressesResource(http: HttpClient): AddressesResource {\n  return new AddressesResource(http);\n}\n","/**\n * NFE.io SDK v3 - Transportation Invoices Resource\n *\n * Handles CT-e (Conhecimento de Transporte Eletrônico) operations via Distribuição DFe\n * Uses a separate API host: api.nfse.io\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  TransportationInvoiceInboundSettings,\n  TransportationInvoiceMetadata,\n  EnableTransportationInvoiceOptions,\n  InboundFileResource\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Base URL for CT-e API */\nexport const CTE_API_BASE_URL = 'https://api.nfse.io';\n\n/** Regex pattern for valid access key (44 numeric digits) */\nconst ACCESS_KEY_PATTERN = /^\\d{44}$/;\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Validates access key format (44 numeric digits)\n * @param accessKey - The CT-e access key to validate\n * @throws {ValidationError} If access key format is invalid\n */\nfunction validateAccessKey(accessKey: string): void {\n  if (!accessKey || accessKey.trim() === '') {\n    throw new ValidationError('Access key is required');\n  }\n\n  const normalized = accessKey.trim();\n  if (!ACCESS_KEY_PATTERN.test(normalized)) {\n    throw new ValidationError(\n      `Invalid access key: \"${accessKey}\". Expected 44 numeric digits.`\n    );\n  }\n}\n\n/**\n * Validates company ID is not empty\n * @param companyId - The company ID to validate\n * @throws {ValidationError} If company ID is empty\n */\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\n// ============================================================================\n// Transportation Invoices Resource\n// ============================================================================\n\n/**\n * Transportation Invoices (CT-e) API Resource\n *\n * @description\n * Provides operations for managing CT-e (Conhecimento de Transporte Eletrônico)\n * documents via SEFAZ Distribuição DFe. This allows companies to automatically\n * receive CT-e documents destined to them.\n *\n * **Prerequisites:**\n * - Company must be registered with a valid A1 digital certificate\n * - Webhook must be configured to receive CT-e notifications\n *\n * **Note:** This resource uses a different API host (api.nfse.io) and may require\n * a separate API key configured via `dataApiKey` in the client configuration.\n * If not set, it falls back to `apiKey`.\n *\n * @example Enable automatic CT-e search\n * ```typescript\n * // Enable with default settings\n * const settings = await nfe.transportationInvoices.enable('company-id');\n *\n * // Enable starting from a specific NSU\n * const settings = await nfe.transportationInvoices.enable('company-id', {\n *   startFromNsu: 12345\n * });\n * ```\n *\n * @example Retrieve CT-e by access key\n * ```typescript\n * const cte = await nfe.transportationInvoices.retrieve(\n *   'company-id',\n *   '35240112345678000190570010000001231234567890'\n * );\n * console.log(cte.nameSender, cte.totalInvoiceAmount);\n * ```\n *\n * @example Download CT-e XML\n * ```typescript\n * const xml = await nfe.transportationInvoices.downloadXml(\n *   'company-id',\n *   '35240112345678000190570010000001231234567890'\n * );\n * // Save to file or parse as needed\n * ```\n */\nexport class TransportationInvoicesResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Automatic Search Management\n  // --------------------------------------------------------------------------\n\n  /**\n   * Enable automatic CT-e search for a company\n   *\n   * Activates the automatic search for CT-e documents destined to the specified\n   * company via SEFAZ Distribuição DFe. Once enabled, new CT-es will be automatically\n   * retrieved and can be accessed via the configured webhook.\n   *\n   * @param companyId - The company ID to enable automatic search for\n   * @param options - Optional settings for the automatic search\n   * @returns Promise with the inbound settings after enabling\n   * @throws {ValidationError} If company ID is empty\n   * @throws {BadRequestError} If the request is invalid\n   * @throws {NotFoundError} If the company is not found\n   *\n   * @example\n   * ```typescript\n   * // Enable with default settings\n   * const settings = await nfe.transportationInvoices.enable('company-id');\n   *\n   * // Enable starting from a specific NSU\n   * const settings = await nfe.transportationInvoices.enable('company-id', {\n   *   startFromNsu: 12345\n   * });\n   *\n   * // Enable starting from a specific date\n   * const settings = await nfe.transportationInvoices.enable('company-id', {\n   *   startFromDate: '2024-01-01T00:00:00Z'\n   * });\n   * ```\n   */\n  async enable(\n    companyId: string,\n    options?: EnableTransportationInvoiceOptions\n  ): Promise<TransportationInvoiceInboundSettings> {\n    validateCompanyId(companyId);\n\n    const response = await this.http.post<TransportationInvoiceInboundSettings>(\n      `/v2/companies/${companyId}/inbound/transportationinvoices`,\n      options || {}\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Disable automatic CT-e search for a company\n   *\n   * Deactivates the automatic search for CT-e documents. After disabling,\n   * no new CT-es will be retrieved for the company.\n   *\n   * @param companyId - The company ID to disable automatic search for\n   * @returns Promise with the inbound settings after disabling\n   * @throws {ValidationError} If company ID is empty\n   * @throws {NotFoundError} If automatic search is not enabled for this company\n   *\n   * @example\n   * ```typescript\n   * const settings = await nfe.transportationInvoices.disable('company-id');\n   * console.log('Automatic search disabled:', settings.status);\n   * ```\n   */\n  async disable(companyId: string): Promise<TransportationInvoiceInboundSettings> {\n    validateCompanyId(companyId);\n\n    const response = await this.http.delete<TransportationInvoiceInboundSettings>(\n      `/v2/companies/${companyId}/inbound/transportationinvoices`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Get current automatic CT-e search settings\n   *\n   * Retrieves the current configuration for automatic CT-e search,\n   * including status, start NSU, start date, and timestamps.\n   *\n   * @param companyId - The company ID to get settings for\n   * @returns Promise with the current inbound settings\n   * @throws {ValidationError} If company ID is empty\n   * @throws {NotFoundError} If automatic search is not configured for this company\n   *\n   * @example\n   * ```typescript\n   * const settings = await nfe.transportationInvoices.getSettings('company-id');\n   * console.log('Status:', settings.status);\n   * console.log('Start NSU:', settings.startFromNsu);\n   * console.log('Created:', settings.createdOn);\n   * ```\n   */\n  async getSettings(companyId: string): Promise<TransportationInvoiceInboundSettings> {\n    validateCompanyId(companyId);\n\n    const response = await this.http.get<TransportationInvoiceInboundSettings>(\n      `/v2/companies/${companyId}/inbound/transportationinvoices`\n    );\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // CT-e Document Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Retrieve CT-e metadata by access key\n   *\n   * Gets the metadata of a CT-e document by its 44-digit access key.\n   *\n   * @param companyId - The company ID that received the CT-e\n   * @param accessKey - The 44-digit CT-e access key\n   * @returns Promise with the CT-e metadata\n   * @throws {ValidationError} If company ID or access key is invalid\n   * @throws {NotFoundError} If the CT-e is not found\n   *\n   * @example\n   * ```typescript\n   * const cte = await nfe.transportationInvoices.retrieve(\n   *   'company-id',\n   *   '35240112345678000190570010000001231234567890'\n   * );\n   * console.log('Sender:', cte.nameSender);\n   * console.log('CNPJ:', cte.federalTaxNumberSender);\n   * console.log('Amount:', cte.totalInvoiceAmount);\n   * console.log('Issued:', cte.issuedOn);\n   * ```\n   */\n  async retrieve(\n    companyId: string,\n    accessKey: string\n  ): Promise<TransportationInvoiceMetadata> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    const response = await this.http.get<TransportationInvoiceMetadata>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Download CT-e XML by access key\n   *\n   * Gets the XML content of a CT-e document.\n   *\n   *\n   * A resposta e um objeto com `publicTemporaryUri` — URL pre-assinada e temporaria.\n   * Binario NAO trafega nesta rota e o `Accept` nao altera a resposta; baixar a URL\n   * fica a cargo do chamador. Verificado ao vivo em 2026-09-01\n   * (tests/fixtures/live-contracts/inbound-download.json).\n   *\n   * @param companyId - The company ID that received the CT-e\n   * @param accessKey - The 44-digit CT-e access key\n   * @returns Promise com o file-resource (`publicTemporaryUri`)\n   * @throws {ValidationError} If company ID or access key is invalid\n   * @throws {NotFoundError} If the CT-e is not found\n   *\n   * @example\n   * ```typescript\n   * const res = await nfe.transportationInvoices.downloadXml(\n   *   'company-id',\n   *   '35240112345678000190570010000001231234567890'\n   * );\n   * const xml = await fetch(res.publicTemporaryUri!).then((r) => r.text());\n   * ```\n   */\n  async downloadXml(companyId: string, accessKey: string): Promise<InboundFileResource> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    const response = await this.http.get<InboundFileResource>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}/xml`\n    );\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // CT-e Event Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Retrieve CT-e event metadata\n   *\n   * Gets the metadata of an event related to a CT-e document.\n   *\n   * @param companyId - The company ID that received the CT-e\n   * @param accessKey - The 44-digit CT-e access key\n   * @param eventKey - The event key\n   * @returns Promise with the event metadata\n   * @throws {ValidationError} If any parameter is invalid\n   * @throws {NotFoundError} If the event is not found\n   *\n   * @example\n   * ```typescript\n   * const event = await nfe.transportationInvoices.getEvent(\n   *   'company-id',\n   *   '35240112345678000190570010000001231234567890',\n   *   'event-key-123'\n   * );\n   * console.log('Event:', event.description);\n   * ```\n   */\n  async getEvent(\n    companyId: string,\n    accessKey: string,\n    eventKey: string\n  ): Promise<TransportationInvoiceMetadata> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    if (!eventKey || eventKey.trim() === '') {\n      throw new ValidationError('Event key is required');\n    }\n\n    const response = await this.http.get<TransportationInvoiceMetadata>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}/events/${eventKey.trim()}`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Download CT-e event XML\n   *\n   * Gets the XML content of a CT-e event.\n   *\n   * @param companyId - The company ID that received the CT-e\n   * @param accessKey - The 44-digit CT-e access key\n   * @param eventKey - The event key\n   * @returns Promise com o file-resource (`publicTemporaryUri`)\n   * @throws {ValidationError} If any parameter is invalid\n   * @throws {NotFoundError} If the event is not found\n   *\n   * @example\n   * ```typescript\n   * const res = await nfe.transportationInvoices.downloadEventXml(\n   *   'company-id',\n   *   '35240112345678000190570010000001231234567890',\n   *   'event-key-123'\n   * );\n   * const xml = await fetch(res.publicTemporaryUri!).then((r) => r.text());\n   * ```\n   *\n   * A resposta e um objeto com `publicTemporaryUri` — URL pre-assinada e temporaria.\n   * Binario NAO trafega nesta rota e o `Accept` nao altera a resposta; baixar a URL\n   * fica a cargo do chamador. Verificado ao vivo em 2026-09-01\n   * (tests/fixtures/live-contracts/inbound-download.json).\n   */\n  async downloadEventXml(\n    companyId: string,\n    accessKey: string,\n    eventKey: string\n  ): Promise<InboundFileResource> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    if (!eventKey || eventKey.trim() === '') {\n      throw new ValidationError('Event key is required');\n    }\n\n    const response = await this.http.get<InboundFileResource>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}/events/${eventKey.trim()}/xml`\n    );\n\n    return response.data;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Creates a TransportationInvoicesResource instance\n *\n * @param http - HTTP client configured for the CT-e API\n * @returns TransportationInvoicesResource instance\n */\nexport function createTransportationInvoicesResource(\n  http: HttpClient\n): TransportationInvoicesResource {\n  return new TransportationInvoicesResource(http);\n}\n","/**\n * NFE.io SDK v3 - Inbound Product Invoices Resource\n *\n * Handles NF-e (Nota Fiscal Eletrônica) distribution queries via Distribuição DFe.\n * Uses the API host: api.nfse.io\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  InboundInvoiceMetadata,\n  InboundProductInvoiceMetadata,\n  InboundSettings,\n  InboundFileResource,\n  EnableInboundOptions,\n  ManifestEventType\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Regex pattern for valid access key (44 numeric digits) */\nconst ACCESS_KEY_PATTERN = /^\\d{44}$/;\n\n/** Default manifest event type: Ciência da Operação */\nconst DEFAULT_MANIFEST_EVENT_TYPE: ManifestEventType = 210210;\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Validates company ID is not empty\n * @param companyId - The company ID to validate\n * @throws {ValidationError} If company ID is empty\n */\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\n/**\n * Validates access key format (44 numeric digits)\n * @param accessKey - The access key to validate\n * @throws {ValidationError} If access key format is invalid\n */\nfunction validateAccessKey(accessKey: string): void {\n  if (!accessKey || accessKey.trim() === '') {\n    throw new ValidationError('Access key is required');\n  }\n\n  const normalized = accessKey.trim();\n  if (!ACCESS_KEY_PATTERN.test(normalized)) {\n    throw new ValidationError(\n      `Invalid access key: \"${accessKey}\". Expected 44 numeric digits.`\n    );\n  }\n}\n\n/**\n * Validates event key is not empty\n * @param eventKey - The event key to validate\n * @throws {ValidationError} If event key is empty\n */\nfunction validateEventKey(eventKey: string): void {\n  if (!eventKey || eventKey.trim() === '') {\n    throw new ValidationError('Event key is required');\n  }\n}\n\n/**\n * Validates access key or NSU identifier is not empty\n * @param accessKeyOrNsu - The identifier to validate\n * @throws {ValidationError} If identifier is empty\n */\nfunction validateAccessKeyOrNsu(accessKeyOrNsu: string): void {\n  if (!accessKeyOrNsu || accessKeyOrNsu.trim() === '') {\n    throw new ValidationError('Access key or NSU is required');\n  }\n}\n\n// ============================================================================\n// Inbound Product Invoices Resource\n// ============================================================================\n\n/**\n * Inbound Product Invoices (NF-e Distribution) API Resource\n *\n * @description\n * Provides operations for querying NF-e (Nota Fiscal Eletrônica) documents\n * received by a company via the SEFAZ Distribuição DFe service.\n *\n * **Capabilities:**\n * - Enable/disable automatic NF-e distribution fetch\n * - Retrieve inbound NF-e metadata by access key\n * - Download NF-e documents in XML, PDF, and JSON formats\n * - Send recipient manifest (Manifestação do Destinatário)\n * - Reprocess webhooks\n *\n * **Prerequisites:**\n * - Company must be registered with a valid A1 digital certificate\n * - Webhook must be configured to receive NF-e notifications\n *\n * **Note:** This resource uses a different API host (api.nfse.io) and may require\n * a separate API key configured via `dataApiKey` in the client configuration.\n * If not set, it falls back to `apiKey`.\n *\n * @example Enable automatic NF-e search\n * ```typescript\n * const settings = await nfe.inboundProductInvoices.enableAutoFetch('company-id', {\n *   startFromNsu: '999999',\n *   environmentSEFAZ: 'Production',\n *   webhookVersion: '2'\n * });\n * ```\n *\n * @example Retrieve NF-e details\n * ```typescript\n * const details = await nfe.inboundProductInvoices.getProductInvoiceDetails(\n *   'company-id',\n *   '35240112345678000190550010000001231234567890'\n * );\n * console.log(details.nameSender, details.totalInvoiceAmount);\n * ```\n *\n * @example Download NF-e XML\n * ```typescript\n * const xml = await nfe.inboundProductInvoices.getXml(\n *   'company-id',\n *   '35240112345678000190550010000001231234567890'\n * );\n * ```\n */\nexport class InboundProductInvoicesResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Automatic Search Management\n  // --------------------------------------------------------------------------\n\n  /**\n   * Enable automatic NF-e distribution fetch for a company\n   *\n   * Activates the automatic search for NF-e documents destined to the specified\n   * company via SEFAZ Distribuição DFe. Once enabled, new NF-e documents will be\n   * automatically retrieved and sent to the configured webhook endpoint.\n   *\n   * @param companyId - The company ID to enable automatic search for\n   * @param options - Configuration options for the automatic search\n   * @returns Promise with the inbound settings after enabling\n   * @throws {ValidationError} If company ID is empty\n   * @throws {BadRequestError} If the request is invalid\n   * @throws {NotFoundError} If the company is not found\n   *\n   * @example\n   * ```typescript\n   * const settings = await nfe.inboundProductInvoices.enableAutoFetch('company-id', {\n   *   startFromNsu: '999999',\n   *   startFromDate: '2024-01-01T00:00:00Z',\n   *   environmentSEFAZ: 'Production',\n   *   automaticManifesting: { minutesToWaitAwarenessOperation: '30' },\n   *   webhookVersion: '2'\n   * });\n   * console.log('Status:', settings.status);\n   * ```\n   */\n  async enableAutoFetch(\n    companyId: string,\n    options: EnableInboundOptions\n  ): Promise<InboundSettings> {\n    validateCompanyId(companyId);\n\n    const response = await this.http.post<InboundSettings>(\n      `/v2/companies/${companyId}/inbound/productinvoices`,\n      options\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Disable automatic NF-e distribution fetch for a company\n   *\n   * Deactivates the automatic search for NF-e documents. After disabling,\n   * no new NF-e documents will be retrieved for the company.\n   *\n   * @param companyId - The company ID to disable automatic search for\n   * @returns Promise with the inbound settings after disabling\n   * @throws {ValidationError} If company ID is empty\n   * @throws {NotFoundError} If automatic search is not enabled for this company\n   *\n   * @example\n   * ```typescript\n   * const settings = await nfe.inboundProductInvoices.disableAutoFetch('company-id');\n   * console.log('Disabled. Status:', settings.status);\n   * ```\n   */\n  async disableAutoFetch(companyId: string): Promise<InboundSettings> {\n    validateCompanyId(companyId);\n\n    const response = await this.http.delete<InboundSettings>(\n      `/v2/companies/${companyId}/inbound/productinvoices`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Get current automatic NF-e distribution fetch settings\n   *\n   * Retrieves the current configuration for automatic NF-e search,\n   * including status, start NSU, start date, and timestamps.\n   *\n   * @param companyId - The company ID to get settings for\n   * @returns Promise with the current inbound settings\n   * @throws {ValidationError} If company ID is empty\n   * @throws {NotFoundError} If automatic search is not configured for this company\n   *\n   * @example\n   * ```typescript\n   * const settings = await nfe.inboundProductInvoices.getSettings('company-id');\n   * console.log('Status:', settings.status);\n   * console.log('Start NSU:', settings.startFromNsu);\n   * console.log('Webhook version:', settings.webhookVersion);\n   * ```\n   */\n  async getSettings(companyId: string): Promise<InboundSettings> {\n    validateCompanyId(companyId);\n\n    const response = await this.http.get<InboundSettings>(\n      `/v2/companies/${companyId}/inbound/productinvoices`\n    );\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Document Detail Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Get details of an inbound NF-e/CT-e by access key (webhook v1 format)\n   *\n   * Retrieves the metadata of an inbound document using its 44-digit access key.\n   * This is the generic endpoint that works for both NF-e and CT-e documents.\n   *\n   * @param companyId - The company ID that received the document\n   * @param accessKey - The 44-digit access key\n   * @returns Promise with the inbound invoice metadata\n   * @throws {ValidationError} If company ID or access key is invalid\n   * @throws {NotFoundError} If the document is not found\n   *\n   * @example\n   * ```typescript\n   * const doc = await nfe.inboundProductInvoices.getDetails(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * console.log('Sender:', doc.nameSender);\n   * console.log('Amount:', doc.totalInvoiceAmount);\n   * console.log('NSU:', doc.nsu);\n   * ```\n   */\n  async getDetails(\n    companyId: string,\n    accessKey: string\n  ): Promise<InboundInvoiceMetadata> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    const response = await this.http.get<InboundInvoiceMetadata>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Get details of an inbound NF-e by access key (webhook v2 format)\n   *\n   * Retrieves the metadata of an NF-e document using its 44-digit access key.\n   * This endpoint returns additional `productInvoices` array compared to the v1 format.\n   *\n   * @param companyId - The company ID that received the document\n   * @param accessKey - The 44-digit access key\n   * @returns Promise with the inbound product invoice metadata (includes productInvoices array)\n   * @throws {ValidationError} If company ID or access key is invalid\n   * @throws {NotFoundError} If the document is not found\n   *\n   * @example\n   * ```typescript\n   * const doc = await nfe.inboundProductInvoices.getProductInvoiceDetails(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * console.log('Sender:', doc.nameSender);\n   * console.log('Product invoices:', doc.productInvoices.length);\n   * ```\n   */\n  async getProductInvoiceDetails(\n    companyId: string,\n    accessKey: string\n  ): Promise<InboundProductInvoiceMetadata> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    const response = await this.http.get<InboundProductInvoiceMetadata>(\n      `/v2/companies/${companyId}/inbound/productinvoice/${accessKey.trim()}`\n    );\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Event Detail Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Get details of an event related to an inbound NF-e/CT-e (generic endpoint)\n   *\n   * Retrieves the metadata of an event associated with an inbound document.\n   *\n   * @param companyId - The company ID that received the document\n   * @param accessKey - The 44-digit access key of the parent document\n   * @param eventKey - The event key\n   * @returns Promise with the event metadata\n   * @throws {ValidationError} If any parameter is invalid\n   * @throws {NotFoundError} If the event is not found\n   *\n   * @example\n   * ```typescript\n   * const event = await nfe.inboundProductInvoices.getEventDetails(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890',\n   *   'event-key-123'\n   * );\n   * console.log('Event:', event.description);\n   * ```\n   */\n  async getEventDetails(\n    companyId: string,\n    accessKey: string,\n    eventKey: string\n  ): Promise<InboundInvoiceMetadata> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n    validateEventKey(eventKey);\n\n    const response = await this.http.get<InboundInvoiceMetadata>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}/events/${eventKey.trim()}`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Get details of an event related to an inbound NF-e (product invoice endpoint)\n   *\n   * Retrieves the metadata of an event associated with an inbound NF-e document.\n   * Returns the webhook v2 format with `productInvoices` array.\n   *\n   * @param companyId - The company ID that received the document\n   * @param accessKey - The 44-digit access key of the parent document\n   * @param eventKey - The event key\n   * @returns Promise with the product invoice event metadata\n   * @throws {ValidationError} If any parameter is invalid\n   * @throws {NotFoundError} If the event is not found\n   *\n   * @example\n   * ```typescript\n   * const event = await nfe.inboundProductInvoices.getProductInvoiceEventDetails(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890',\n   *   'event-key-123'\n   * );\n   * console.log('Event:', event.description);\n   * console.log('Product invoices:', event.productInvoices.length);\n   * ```\n   */\n  async getProductInvoiceEventDetails(\n    companyId: string,\n    accessKey: string,\n    eventKey: string\n  ): Promise<InboundProductInvoiceMetadata> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n    validateEventKey(eventKey);\n\n    const response = await this.http.get<InboundProductInvoiceMetadata>(\n      `/v2/companies/${companyId}/inbound/productinvoice/${accessKey.trim()}/events/${eventKey.trim()}`\n    );\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // File Download Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Download XML of an inbound NF-e/CT-e by access key\n   *\n   * Gets the XML content of an inbound document.\n   *\n   * A resposta e um objeto com `publicTemporaryUri` — URL pre-assinada e temporaria.\n   * Binario NAO trafega nesta rota e o `Accept` nao altera a resposta; baixar a URL\n   * fica a cargo do chamador. Verificado ao vivo em 2026-09-01\n   * (tests/fixtures/live-contracts/inbound-download.json).\n   *\n   * @param companyId - The company ID that received the document\n   * @param accessKey - The 44-digit access key\n   * @returns Promise com o file-resource (`publicTemporaryUri`)\n   * @throws {ValidationError} If company ID or access key is invalid\n   * @throws {NotFoundError} If the document is not found\n   *\n   * @example\n   * ```typescript\n   * const res = await nfe.inboundProductInvoices.getXml(companyId, accessKey);\n   * const doc = await fetch(res.publicTemporaryUri!).then((r) => r.text());\n   * ```\n   */\n  async getXml(companyId: string, accessKey: string): Promise<InboundFileResource> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    const response = await this.http.get<InboundFileResource>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}/xml`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Download XML of an event related to an inbound NF-e/CT-e\n   *\n   * Gets the XML content of an event associated with an inbound document.\n   *\n   * A resposta e um objeto com `publicTemporaryUri` — URL pre-assinada e temporaria.\n   * Binario NAO trafega nesta rota e o `Accept` nao altera a resposta; baixar a URL\n   * fica a cargo do chamador. Verificado ao vivo em 2026-09-01\n   * (tests/fixtures/live-contracts/inbound-download.json).\n   *\n   * @param companyId - The company ID that received the document\n   * @param accessKey - The 44-digit access key of the parent document\n   * @param eventKey - The event key\n   * @returns Promise with the event XML content as a string\n   * @throws {ValidationError} If any parameter is invalid\n   * @throws {NotFoundError} If the event is not found\n   *\n   * @example\n   * ```typescript\n   * const res = await nfe.inboundProductInvoices.getEventXml(companyId, accessKey, eventKey);\n   * const doc = await fetch(res.publicTemporaryUri!).then((r) => r.text());\n   * ```\n   */\n  async getEventXml(\n    companyId: string,\n    accessKey: string,\n    eventKey: string\n  ): Promise<InboundFileResource> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n    validateEventKey(eventKey);\n\n    const response = await this.http.get<InboundFileResource>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}/events/${eventKey.trim()}/xml`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Download PDF of an inbound NF-e by access key\n   *\n   * Gets the PDF content of an NF-e document.\n   *\n   * A resposta e um objeto com `publicTemporaryUri` — URL pre-assinada e temporaria.\n   * Binario NAO trafega nesta rota e o `Accept` nao altera a resposta; baixar a URL\n   * fica a cargo do chamador. Verificado ao vivo em 2026-09-01\n   * (tests/fixtures/live-contracts/inbound-download.json).\n   *\n   * @param companyId - The company ID that received the document\n   * @param accessKey - The 44-digit access key\n   * @returns Promise com o file-resource (`publicTemporaryUri`)\n   * @throws {ValidationError} If company ID or access key is invalid\n   * @throws {NotFoundError} If the document is not found\n   *\n   * @example\n   * ```typescript\n   * const res = await nfe.inboundProductInvoices.getPdf(companyId, accessKey);\n   * const bytes = await fetch(res.publicTemporaryUri!).then((r) => r.arrayBuffer());\n   * ```\n   */\n  async getPdf(companyId: string, accessKey: string): Promise<InboundFileResource> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    const response = await this.http.get<InboundFileResource>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}/pdf`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Get JSON representation of an inbound NF-e by access key\n   *\n   * Gets the structured JSON data of an NF-e document.\n   *\n   * @param companyId - The company ID that received the document\n   * @param accessKey - The 44-digit access key\n   * @returns Promise with the NF-e metadata in JSON format\n   * @throws {ValidationError} If company ID or access key is invalid\n   * @throws {NotFoundError} If the document is not found\n   *\n   * @example\n   * ```typescript\n   * const data = await nfe.inboundProductInvoices.getJson(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * console.log('Sender:', data.nameSender);\n   * console.log('Amount:', data.totalInvoiceAmount);\n   * ```\n   */\n  async getJson(\n    companyId: string,\n    accessKey: string\n  ): Promise<InboundInvoiceMetadata> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    const response = await this.http.get<InboundInvoiceMetadata>(\n      `/v2/companies/${companyId}/inbound/productinvoice/${accessKey.trim()}/json`\n    );\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Manifest Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Send recipient manifest (Manifestação do Destinatário) for an NF-e\n   *\n   * Sends a manifest event for an NF-e document identified by its access key.\n   * Defaults to \"Ciência da Operação\" (210210) if no event type is specified.\n   *\n   * **Event types:**\n   * - `210210` — Ciência da Operação (awareness, default)\n   * - `210220` — Confirmação da Operação (confirmation)\n   * - `210240` — Operação não Realizada (operation not performed)\n   *\n   * @param companyId - The company ID\n   * @param accessKey - The 44-digit access key of the NF-e\n   * @param tpEvent - Manifest event type (defaults to 210210)\n   * @returns Promise with the manifest response\n   * @throws {ValidationError} If company ID or access key is invalid\n   *\n   * @example Default manifest (Ciência da Operação)\n   * ```typescript\n   * const result = await nfe.inboundProductInvoices.manifest(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * ```\n   *\n   * @example Confirm operation\n   * ```typescript\n   * const result = await nfe.inboundProductInvoices.manifest(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890',\n   *   210220\n   * );\n   * ```\n   */\n  async manifest(\n    companyId: string,\n    accessKey: string,\n    tpEvent: ManifestEventType = DEFAULT_MANIFEST_EVENT_TYPE\n  ): Promise<string> {\n    validateCompanyId(companyId);\n    validateAccessKey(accessKey);\n\n    const response = await this.http.post<string>(\n      `/v2/companies/${companyId}/inbound/${accessKey.trim()}/manifest?tpEvent=${tpEvent}`\n    );\n\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Webhook Operations\n  // --------------------------------------------------------------------------\n\n  /**\n   * Reprocess webhook for an inbound NF-e by access key or NSU\n   *\n   * Triggers reprocessing of the webhook notification for a specific document,\n   * identified either by its 44-digit access key or by its NSU number.\n   *\n   * @param companyId - The company ID\n   * @param accessKeyOrNsu - The 44-digit access key or NSU number\n   * @returns Promise with the product invoice metadata\n   * @throws {ValidationError} If company ID or identifier is empty\n   * @throws {NotFoundError} If the document is not found\n   *\n   * @example Reprocess by access key\n   * ```typescript\n   * const result = await nfe.inboundProductInvoices.reprocessWebhook(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * ```\n   *\n   * @example Reprocess by NSU\n   * ```typescript\n   * const result = await nfe.inboundProductInvoices.reprocessWebhook(\n   *   'company-id',\n   *   '12345'\n   * );\n   * ```\n   */\n  async reprocessWebhook(\n    companyId: string,\n    accessKeyOrNsu: string\n  ): Promise<InboundProductInvoiceMetadata> {\n    validateCompanyId(companyId);\n    validateAccessKeyOrNsu(accessKeyOrNsu);\n\n    const response = await this.http.post<InboundProductInvoiceMetadata>(\n      `/v2/companies/${companyId}/inbound/productinvoice/${accessKeyOrNsu.trim()}/processwebhook`\n    );\n\n    return response.data;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Creates an InboundProductInvoicesResource instance\n *\n * @param http - HTTP client configured for the inbound API (api.nfse.io)\n * @returns InboundProductInvoicesResource instance\n */\nexport function createInboundProductInvoicesResource(\n  http: HttpClient\n): InboundProductInvoicesResource {\n  return new InboundProductInvoicesResource(http);\n}\n","/**\n * NFE.io SDK v3 - Product Invoice Query Resource\n *\n * Queries NF-e (Nota Fiscal Eletrônica) product invoices directly on SEFAZ\n * by access key. Read-only lookups — no company scope required.\n * Uses the API host: nfe.api.nfe.io\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  ProductInvoiceDetails,\n  ProductInvoiceEventsResponse,\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Base URL for NF-e Query API */\nexport const NFE_QUERY_API_BASE_URL = 'https://nfe.api.nfe.io';\n\n/** Regex pattern for valid access key (44 numeric digits) */\nconst ACCESS_KEY_PATTERN = /^\\d{44}$/;\n\n/**\n * `Accept` dos downloads por chave de acesso.\n *\n * O tipo binário vem primeiro, então o caminho feliz não muda: sucesso continua\n * respondendo `200` com o mesmo `content-type` e os mesmos bytes. O\n * `application/json` de segunda escolha existe para o caminho de ERRO — sem ele,\n * o servidor não tem formatter de erro para PDF e responde **406 com corpo\n * vazio**, apagando a mensagem real. Medido em 2026-09-02:\n *\n *   .pdf + \"application/pdf\"                          -> chave real: 200 %PDF-1.4\n *                                                        chave inexistente: 406, corpo vazio\n *   .pdf + \"application/pdf, application/json;q=0.9\"  -> chave real: 200 %PDF-1.4 (mesmos bytes)\n *                                                        chave inexistente: 400 {\"errors\":[{\"message\":\"access key is not valid\"}]}\n */\nconst ACCEPT_PDF = 'application/pdf, application/json;q=0.9';\n\n/** Idem para XML. Aqui já havia formatter de erro XML; vale por consistência. */\nconst ACCEPT_XML = 'application/xml, application/json;q=0.9';\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Validates access key format (44 numeric digits)\n * @param accessKey - The access key to validate\n * @throws {ValidationError} If access key is empty or has invalid format\n */\nfunction validateAccessKey(accessKey: string): void {\n  if (!accessKey || accessKey.trim() === '') {\n    throw new ValidationError('Access key is required');\n  }\n\n  const normalized = accessKey.trim();\n  if (!ACCESS_KEY_PATTERN.test(normalized)) {\n    throw new ValidationError(\n      `Invalid access key: \"${accessKey}\". Expected 44 numeric digits.`\n    );\n  }\n}\n\n// ============================================================================\n// Resource Implementation\n// ============================================================================\n\n/**\n * Product Invoice Query Resource\n *\n * @description\n * Queries NF-e (Nota Fiscal Eletrônica) product invoices on SEFAZ by access key.\n * This is a read-only resource that does not require company scope.\n *\n * **Capabilities:**\n * - Retrieve full invoice details (issuer, buyer, items, totals, transport, payment)\n * - Download DANFE PDF\n * - Download NF-e XML\n * - List fiscal events (cancellations, corrections, manifestations)\n *\n * **Authentication:** Uses data API key (`dataApiKey` or `apiKey` fallback).\n *\n * @example\n * ```typescript\n * const details = await nfe.productInvoiceQuery.retrieve(\n *   '35240112345678000190550010000001231234567890'\n * );\n * console.log(details.issuer?.name, details.totals?.icms?.invoiceAmount);\n * ```\n */\nexport class ProductInvoiceQueryResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Public Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Retrieve full product invoice (NF-e) details from SEFAZ by access key\n   *\n   * @param accessKey - 44-digit numeric access key (Chave de Acesso)\n   * @returns Full invoice details including issuer, buyer, items, totals, transport, and payment\n   * @throws {ValidationError} If access key format is invalid\n   * @throws {NotFoundError} If no invoice matches the access key (HTTP 404)\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const invoice = await nfe.productInvoiceQuery.retrieve(\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * console.log(invoice.currentStatus); // 'authorized'\n   * console.log(invoice.issuer?.name);\n   * console.log(invoice.totals?.icms?.invoiceAmount);\n   * ```\n   */\n  async retrieve(accessKey: string): Promise<ProductInvoiceDetails> {\n    validateAccessKey(accessKey);\n    const response = await this.http.get<ProductInvoiceDetails>(\n      `/v2/productinvoices/${accessKey.trim()}`\n    );\n    return response.data;\n  }\n\n  /**\n   * Download the DANFE PDF for a product invoice by access key\n   *\n   * @param accessKey - 44-digit numeric access key (Chave de Acesso)\n   * @returns Buffer containing the PDF binary content\n   * @throws {ValidationError} If access key format is invalid\n   * @throws {NotFoundError} If no invoice matches the access key (HTTP 404)\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const pdfBuffer = await nfe.productInvoiceQuery.downloadPdf(\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * fs.writeFileSync('danfe.pdf', pdfBuffer);\n   * ```\n   */\n  async downloadPdf(accessKey: string): Promise<Buffer> {\n    validateAccessKey(accessKey);\n    const response = await this.http.getBuffer(\n      `/v2/productinvoices/${accessKey.trim()}.pdf`,\n      ACCEPT_PDF\n    );\n    return response.data;\n  }\n\n  /**\n   * Download the raw NF-e XML for a product invoice by access key\n   *\n   * @param accessKey - 44-digit numeric access key (Chave de Acesso)\n   * @returns Buffer containing the XML binary content\n   * @throws {ValidationError} If access key format is invalid\n   * @throws {NotFoundError} If no invoice matches the access key (HTTP 404)\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const xmlBuffer = await nfe.productInvoiceQuery.downloadXml(\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * fs.writeFileSync('nfe.xml', xmlBuffer);\n   * ```\n   */\n  async downloadXml(accessKey: string): Promise<Buffer> {\n    validateAccessKey(accessKey);\n    const response = await this.http.getBuffer(\n      `/v2/productinvoices/${accessKey.trim()}.xml`,\n      ACCEPT_XML\n    );\n    return response.data;\n  }\n\n  /**\n   * List fiscal events for a product invoice by access key\n   *\n   * Events include cancellations, corrections, manifestations, etc.\n   *\n   * @param accessKey - 44-digit numeric access key (Chave de Acesso)\n   * @returns Events response with an array of fiscal events and query timestamp\n   * @throws {ValidationError} If access key format is invalid\n   * @throws {NotFoundError} If no invoice matches the access key (HTTP 404)\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.productInvoiceQuery.listEvents(\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * for (const event of result.events ?? []) {\n   *   console.log(event.description, event.authorizedOn);\n   * }\n   * ```\n   */\n  async listEvents(accessKey: string): Promise<ProductInvoiceEventsResponse> {\n    validateAccessKey(accessKey);\n    const response = await this.http.get<ProductInvoiceEventsResponse>(\n      `/v2/productinvoices/events/${accessKey.trim()}`\n    );\n    return response.data;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Create a new ProductInvoiceQueryResource instance\n */\nexport function createProductInvoiceQueryResource(http: HttpClient): ProductInvoiceQueryResource {\n  return new ProductInvoiceQueryResource(http);\n}\n","/**\n * NFE.io SDK — rotas declaradas na spec que a plataforma não serve.\n *\n * Algumas rotas existem na OpenAPI (e no `nfeio-docs`) e simplesmente não são\n * roteadas em produção. O chamador recebe `404` e não tem como distinguir isso de\n * \"esse dado não existe\" — vai procurar defeito nos próprios dados, ou reportar\n * como bug do SDK.\n *\n * Como a distinção foi feita (2026-09-02):\n *\n * - Comparar com um path inventado no mesmo host. `404` de corpo vazio, sem\n *   `content-type`, byte a byte igual ao do path inventado, é roteamento — não\n *   \"não encontrado\". Rota servida devolve corpo com mensagem.\n * - Confirmação independente: rota servida responde `401` **sem credencial**;\n *   rota não servida responde `404` sem credencial, porque o middleware de\n *   autenticação nem chega a rodar.\n *\n * O SDK **não** bloqueia a chamada no cliente. A requisição sai; só o `404` é\n * enriquecido. Se a rota voltar a ser servida, o `200` passa intacto e nada aqui\n * precisa ser desfeito — um guard antes da requisição congelaria a medição de\n * hoje no código, e ninguém lembraria de removê-lo.\n */\n\nimport { NotFoundError, isNotFoundError } from '../errors/index.js';\n\n/** Quando a ausência da rota foi medida. */\nexport const UNSERVED_ROUTE_MEASURED_ON = '2026-09-02';\n\n/**\n * Executa a chamada e, **somente** em `404`, relança com a explicação.\n *\n * Preserva a classe do erro (`NotFoundError`), para não quebrar quem já trata\n * `instanceof` ou `isNotFoundError()`.\n *\n * @param route - A rota, como aparece na spec\n * @param call - A requisição\n */\nexport async function withUnservedRouteNote<T>(route: string, call: () => Promise<T>): Promise<T> {\n  try {\n    return await call();\n  } catch (error) {\n    if (!isNotFoundError(error)) throw error;\n\n    throw new NotFoundError(\n      `A plataforma não serve a rota ${route} (medido em ${UNSERVED_ROUTE_MEASURED_ON}): ` +\n        'ela está declarada na OpenAPI e responde 404 idêntico ao de um caminho inexistente, ' +\n        'inclusive sem credencial. Não é \"registro não encontrado\" — é rota ausente, e não há ' +\n        'nada a corrigir na chamada. Pendência aberta com o time de API.',\n      error.details\n    );\n  }\n}\n","/**\n * NFE.io SDK v3 - Consumer Invoice Query Resource\n *\n * Queries CFe-SAT (Cupom Fiscal Eletrônico) consumer invoices\n * by access key. Read-only lookups — no company scope required.\n * Uses the API host: nfe.api.nfe.io\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type { TaxCoupon } from '../types.js';\nimport { ValidationError } from '../errors/index.js';\nimport { withUnservedRouteNote } from '../utils/unserved-route.js';\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Regex pattern for valid access key (44 numeric digits) */\nconst ACCESS_KEY_PATTERN = /^\\d{44}$/;\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Validates access key format (44 numeric digits)\n * @param accessKey - The access key to validate\n * @throws {ValidationError} If access key is empty or has invalid format\n */\nfunction validateAccessKey(accessKey: string): void {\n  if (!accessKey || accessKey.trim() === '') {\n    throw new ValidationError('Access key is required');\n  }\n\n  const normalized = accessKey.trim();\n  if (!ACCESS_KEY_PATTERN.test(normalized)) {\n    throw new ValidationError(\n      `Invalid access key: \"${accessKey}\". Expected 44 numeric digits.`\n    );\n  }\n}\n\n// ============================================================================\n// Resource Implementation\n// ============================================================================\n\n/**\n * Consumer Invoice Query Resource\n *\n * @deprecated **A plataforma não serve nenhuma das duas rotas deste recurso.**\n * Elas estão declaradas na spec `consulta-nf-consumidor` e no `nfeio-docs`, em\n * `nfe.api.nfe.io` — e respondem `404` de corpo vazio, sem `content-type`,\n * idêntico ao de um path inventado no mesmo host. Confirmação independente: o\n * `404` vem **inclusive sem credencial**, enquanto uma rota servida no mesmo host\n * responde `401` sem credencial — o middleware de autenticação nem chega a rodar.\n * Noventa dias de log de gateway não têm um único `200`. Medido em 2026-09-02.\n *\n * Os métodos continuam emitindo a requisição: se a rota subir, o resultado passa\n * sem alteração.\n *\n * @description\n * Queries CFe-SAT (Cupom Fiscal Eletrônico) consumer invoices by access key.\n * This is a read-only resource that does not require company scope.\n *\n * **Capabilities:**\n * - Retrieve full coupon details (issuer, buyer, items, totals, payment)\n * - Download original CFe XML\n *\n * **Authentication:** Uses data API key (`dataApiKey` or `apiKey` fallback).\n *\n * @example\n * ```typescript\n * const coupon = await nfe.consumerInvoiceQuery.retrieve(\n *   '35240112345678000190590000000012341234567890'\n * );\n * console.log(coupon.issuer?.name, coupon.totals?.couponAmount);\n * ```\n */\nexport class ConsumerInvoiceQueryResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Public Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Retrieve full CFe-SAT coupon details from SEFAZ by access key\n   *\n   * @param accessKey - 44-digit numeric access key (Chave de Acesso)\n   * @returns Full coupon details including issuer, buyer, items, totals, and payment\n   * @throws {ValidationError} If access key format is invalid\n   * @throws {NotFoundError} If no coupon matches the access key (HTTP 404)\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const coupon = await nfe.consumerInvoiceQuery.retrieve(\n   *   '35240112345678000190590000000012341234567890'\n   * );\n   * console.log(coupon.currentStatus); // 'Authorized'\n   * console.log(coupon.issuer?.name);\n   * console.log(coupon.totals?.couponAmount);\n   * ```\n   */\n  async retrieve(accessKey: string): Promise<TaxCoupon> {\n    validateAccessKey(accessKey);\n    const response = await withUnservedRouteNote(\n      'GET /v1/consumerinvoices/coupon/{accessKey}',\n      () => this.http.get<TaxCoupon>(`/v1/consumerinvoices/coupon/${accessKey.trim()}`)\n    );\n    return response.data;\n  }\n\n  /**\n   * Download the raw CFe XML for a consumer invoice by access key\n   *\n   * @param accessKey - 44-digit numeric access key (Chave de Acesso)\n   * @returns Buffer containing the XML binary content\n   * @throws {ValidationError} If access key format is invalid\n   * @throws {NotFoundError} If no coupon matches the access key (HTTP 404)\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const xmlBuffer = await nfe.consumerInvoiceQuery.downloadXml(\n   *   '35240112345678000190590000000012341234567890'\n   * );\n   * fs.writeFileSync('cfe.xml', xmlBuffer);\n   * ```\n   */\n  async downloadXml(accessKey: string): Promise<Buffer> {\n    validateAccessKey(accessKey);\n    const response = await withUnservedRouteNote(\n      'GET /v1/consumerinvoices/coupon/{accessKey}.xml',\n      () =>\n        this.http.getBuffer(\n          `/v1/consumerinvoices/coupon/${accessKey.trim()}.xml`,\n          // Mesmo motivo do productInvoiceQuery: sem o JSON de segunda escolha, o\n          // erro volta 406 de corpo vazio em vez da mensagem da API.\n          'application/xml, application/json;q=0.9'\n        )\n    );\n    return response.data;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Create a new ConsumerInvoiceQueryResource instance\n */\nexport function createConsumerInvoiceQueryResource(http: HttpClient): ConsumerInvoiceQueryResource {\n  return new ConsumerInvoiceQueryResource(http);\n}\n","/**\n * NFE.io SDK v3 - Legal Entity Lookup Resource\n *\n * Handles CNPJ lookup operations via the Legal Entity API.\n * Uses a separate API host: legalentity.api.nfe.io\n *\n * Provides methods for:\n * - Basic company info lookup by CNPJ\n * - State tax registration (Inscrição Estadual) lookup\n * - State tax evaluation for invoice issuance\n * - Suggested state tax for optimal invoice issuance\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  BrazilianState,\n  LegalEntityBasicInfoOptions,\n  LegalEntityBasicInfoResponse,\n  LegalEntityStateTaxResponse,\n  LegalEntityStateTaxForInvoiceResponse,\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Base URL for Legal Entity API */\nexport const LEGAL_ENTITY_API_BASE_URL = 'https://legalentity.api.nfe.io';\n\n/** Set of valid Brazilian state codes (27 UFs + EX + NA) */\nconst VALID_BRAZILIAN_STATES: ReadonlySet<string> = new Set<string>([\n  'AC', 'AL', 'AM', 'AP', 'BA', 'CE', 'DF', 'ES', 'GO',\n  'MA', 'MG', 'MS', 'MT', 'PA', 'PB', 'PE', 'PI', 'PR',\n  'RJ', 'RN', 'RO', 'RR', 'RS', 'SC', 'SE', 'SP', 'TO',\n  'EX', 'NA',\n]);\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Normalizes a federal tax number (CNPJ) by stripping all non-digit characters.\n *\n * @param federalTaxNumber - Raw CNPJ string, with or without punctuation\n * @returns Digits-only CNPJ string\n */\nfunction normalizeFederalTaxNumber(federalTaxNumber: string): string {\n  return federalTaxNumber.replace(/\\D/g, '');\n}\n\n/**\n * Validates a federal tax number (CNPJ) format.\n * Strips non-digit characters and checks for exactly 14 digits.\n *\n * @param federalTaxNumber - CNPJ string to validate\n * @returns Normalized digits-only CNPJ string\n * @throws {ValidationError} If input is empty or not exactly 14 digits after normalization\n */\nfunction validateFederalTaxNumber(federalTaxNumber: string | undefined | null): string {\n  if (!federalTaxNumber || federalTaxNumber.trim() === '') {\n    throw new ValidationError('Federal tax number (CNPJ) is required');\n  }\n\n  const normalized = normalizeFederalTaxNumber(federalTaxNumber);\n\n  if (normalized.length !== 14) {\n    throw new ValidationError(\n      `Invalid federal tax number format: \"${federalTaxNumber}\". Expected 14 digits (e.g., \"12345678000190\" or \"12.345.678/0001-90\"), got ${normalized.length} digit(s).`\n    );\n  }\n\n  return normalized;\n}\n\n/**\n * Validates a Brazilian state code.\n * Normalizes to uppercase and checks against the valid set.\n *\n * @param state - State code to validate\n * @returns Normalized uppercase state code\n * @throws {ValidationError} If state code is empty or not in the valid set\n */\nfunction validateState(state: string | undefined | null): BrazilianState {\n  if (!state || state.trim() === '') {\n    throw new ValidationError('State code is required');\n  }\n\n  const normalized = state.trim().toUpperCase();\n\n  if (!VALID_BRAZILIAN_STATES.has(normalized)) {\n    const validCodes = Array.from(VALID_BRAZILIAN_STATES).sort().join(', ');\n    throw new ValidationError(\n      `Invalid state code: \"${state}\". Valid codes: ${validCodes}`\n    );\n  }\n\n  return normalized as BrazilianState;\n}\n\n// ============================================================================\n// Legal Entity Lookup Resource\n// ============================================================================\n\n/**\n * Legal Entity Lookup API Resource\n *\n * @description\n * Provides read-only operations for querying Brazilian company (CNPJ) data\n * from the NFE.io Legal Entity API. Data is sourced from Receita Federal,\n * SEFAZ state registries, and NFE.io enrichment services.\n *\n * **Note:** This resource uses a different API host (legalentity.api.nfe.io)\n * and may require a separate API key configured via `dataApiKey` in the client configuration.\n *\n * @example Basic CNPJ lookup\n * ```typescript\n * const result = await nfe.legalEntityLookup.getBasicInfo('12.345.678/0001-90');\n * console.log(result.legalEntity?.name);       // 'EMPRESA LTDA'\n * console.log(result.legalEntity?.status);      // 'Active'\n * console.log(result.legalEntity?.address?.city?.name); // 'São Paulo'\n * ```\n *\n * @example State tax registration lookup\n * ```typescript\n * const result = await nfe.legalEntityLookup.getStateTaxInfo('SP', '12345678000190');\n * for (const tax of result.legalEntity?.stateTaxes ?? []) {\n *   console.log(`IE: ${tax.taxNumber} - Status: ${tax.status}`);\n * }\n * ```\n *\n * @example Best IE for invoice issuance\n * ```typescript\n * const result = await nfe.legalEntityLookup.getSuggestedStateTaxForInvoice('SP', '12345678000190');\n * const bestIE = result.legalEntity?.stateTaxes?.[0];\n * console.log(`Best IE: ${bestIE?.taxNumber} (${bestIE?.status})`);\n * ```\n */\nexport class LegalEntityLookupResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Public Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Lookup basic company information by CNPJ\n   *\n   * @description\n   * Queries the Receita Federal registry for company registration data including\n   * legal name, trade name, address, phone numbers, economic activities (CNAE),\n   * legal nature, partners, registration status, and share capital.\n   *\n   * @param federalTaxNumber - CNPJ number, with or without punctuation (e.g., \"12345678000190\" or \"12.345.678/0001-90\")\n   * @param options - Optional lookup configuration\n   * @returns Promise with company basic information\n   * @throws {ValidationError} If CNPJ format is invalid (not 14 digits)\n   * @throws {NotFoundError} If no company found for the given CNPJ\n   * @throws {AuthenticationError} If API key is invalid or missing\n   *\n   * @example\n   * ```typescript\n   * // Simple lookup\n   * const result = await nfe.legalEntityLookup.getBasicInfo('12345678000190');\n   * console.log(result.legalEntity?.name);\n   *\n   * // With formatted CNPJ\n   * const result = await nfe.legalEntityLookup.getBasicInfo('12.345.678/0001-90');\n   *\n   * // Disable address update from postal service\n   * const result = await nfe.legalEntityLookup.getBasicInfo('12345678000190', {\n   *   updateAddress: false,\n   *   updateCityCode: true\n   * });\n   * ```\n   */\n  async getBasicInfo(\n    federalTaxNumber: string,\n    options?: LegalEntityBasicInfoOptions\n  ): Promise<LegalEntityBasicInfoResponse> {\n    const normalized = validateFederalTaxNumber(federalTaxNumber);\n\n    const params: Record<string, unknown> = {};\n    if (options?.updateAddress !== undefined) {\n      params['updateAddress'] = options.updateAddress;\n    }\n    if (options?.updateCityCode !== undefined) {\n      params['updateCityCode'] = options.updateCityCode;\n    }\n\n    const response = await this.http.get<LegalEntityBasicInfoResponse>(\n      `/v2/legalentities/basicInfo/${normalized}`,\n      Object.keys(params).length > 0 ? params : undefined\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Lookup state tax registration (Inscrição Estadual) by CNPJ and state\n   *\n   * @description\n   * Queries state tax registration data for a given CNPJ in a specific Brazilian state.\n   * Returns registration details including status, tax regime, economic activities,\n   * and fiscal document indicators (NFe, NFSe, CTe, NFCe).\n   *\n   * @param state - Brazilian state abbreviation (e.g., \"SP\", \"RJ\", \"MG\")\n   * @param federalTaxNumber - CNPJ number, with or without punctuation\n   * @returns Promise with state tax registration information\n   * @throws {ValidationError} If state code or CNPJ format is invalid\n   * @throws {AuthenticationError} If API key is invalid or missing\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.legalEntityLookup.getStateTaxInfo('SP', '12345678000190');\n   * console.log(result.legalEntity?.taxRegime);  // 'SimplesNacional'\n   *\n   * for (const tax of result.legalEntity?.stateTaxes ?? []) {\n   *   console.log(`IE: ${tax.taxNumber} - Status: ${tax.status}`);\n   *   console.log(`  NFe: ${tax.nfe?.status}, NFSe: ${tax.nfse?.status}`);\n   * }\n   * ```\n   */\n  async getStateTaxInfo(\n    state: string,\n    federalTaxNumber: string\n  ): Promise<LegalEntityStateTaxResponse> {\n    const normalizedState = validateState(state);\n    const normalizedCnpj = validateFederalTaxNumber(federalTaxNumber);\n\n    const response = await this.http.get<LegalEntityStateTaxResponse>(\n      `/v2/legalentities/stateTaxInfo/${normalizedState}/${normalizedCnpj}`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Lookup state tax registration for invoice issuance evaluation\n   *\n   * @description\n   * Queries state tax registration data specifically for evaluating the ability\n   * to issue product invoices (NF-e) in a given state. Returns extended status\n   * information including temporary and unconfirmed states.\n   *\n   * @param state - Brazilian state abbreviation (e.g., \"SP\", \"RJ\", \"MG\")\n   * @param federalTaxNumber - CNPJ number, with or without punctuation\n   * @returns Promise with state tax data for invoice evaluation\n   * @throws {ValidationError} If state code or CNPJ format is invalid\n   * @throws {AuthenticationError} If API key is invalid or missing\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.legalEntityLookup.getStateTaxForInvoice('MG', '12345678000190');\n   * for (const tax of result.legalEntity?.stateTaxes ?? []) {\n   *   if (tax.status === 'Abled') {\n   *     console.log(`Can issue invoices with IE: ${tax.taxNumber}`);\n   *   }\n   * }\n   * ```\n   */\n  async getStateTaxForInvoice(\n    state: string,\n    federalTaxNumber: string\n  ): Promise<LegalEntityStateTaxForInvoiceResponse> {\n    const normalizedState = validateState(state);\n    const normalizedCnpj = validateFederalTaxNumber(federalTaxNumber);\n\n    const response = await this.http.get<LegalEntityStateTaxForInvoiceResponse>(\n      `/v2/legalentities/stateTaxForInvoice/${normalizedState}/${normalizedCnpj}`\n    );\n\n    return response.data;\n  }\n\n  /**\n   * Lookup the best state tax registration for invoice issuance\n   *\n   * @description\n   * Queries the optimal state tax registration for issuing invoices when multiple\n   * registrations are enabled in a state. NFE.io applies evaluation criteria to\n   * suggest the best IE for invoice issuance.\n   *\n   * Returns the same response type as `getStateTaxForInvoice` but the API\n   * prioritizes the best enabled state tax registration.\n   *\n   * @param state - Brazilian state abbreviation (e.g., \"SP\", \"RJ\", \"MG\")\n   * @param federalTaxNumber - CNPJ number, with or without punctuation\n   * @returns Promise with suggested state tax data for invoice evaluation\n   * @throws {ValidationError} If state code or CNPJ format is invalid\n   * @throws {AuthenticationError} If API key is invalid or missing\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.legalEntityLookup.getSuggestedStateTaxForInvoice('SP', '12345678000190');\n   * const bestIE = result.legalEntity?.stateTaxes?.[0];\n   * if (bestIE) {\n   *   console.log(`Recommended IE: ${bestIE.taxNumber} (${bestIE.status})`);\n   * }\n   * ```\n   */\n  async getSuggestedStateTaxForInvoice(\n    state: string,\n    federalTaxNumber: string\n  ): Promise<LegalEntityStateTaxForInvoiceResponse> {\n    const normalizedState = validateState(state);\n    const normalizedCnpj = validateFederalTaxNumber(federalTaxNumber);\n\n    const response = await this.http.get<LegalEntityStateTaxForInvoiceResponse>(\n      `/v2/legalentities/stateTaxSuggestedForInvoice/${normalizedState}/${normalizedCnpj}`\n    );\n\n    return response.data;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Creates a LegalEntityLookupResource instance\n *\n * @param http - HTTP client configured for the Legal Entity API\n * @returns LegalEntityLookupResource instance\n */\nexport function createLegalEntityLookupResource(http: HttpClient): LegalEntityLookupResource {\n  return new LegalEntityLookupResource(http);\n}\n","/**\n * NFE.io SDK v3 - Natural Person Lookup Resource\n *\n * Handles CPF cadastral status lookup operations via the Natural Person API.\n * Uses a separate API host: naturalperson.api.nfe.io\n *\n * Provides methods for:\n * - CPF cadastral status query (situação cadastral na Receita Federal)\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type { NaturalPersonStatusResponse } from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Base URL for Natural Person API */\nexport const NATURAL_PERSON_API_BASE_URL = 'https://naturalperson.api.nfe.io';\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Normalizes a CPF by stripping all non-digit characters.\n *\n * @param cpf - Raw CPF string, with or without punctuation\n * @returns Digits-only CPF string\n */\nfunction normalizeCpf(cpf: string): string {\n  return cpf.replace(/\\D/g, '');\n}\n\n/**\n * Validates a CPF format.\n * Strips non-digit characters and checks for exactly 11 digits.\n *\n * @param federalTaxNumber - CPF string to validate\n * @returns Normalized digits-only CPF string\n * @throws {ValidationError} If input is empty or not exactly 11 digits after normalization\n */\nfunction validateCpf(federalTaxNumber: string | undefined | null): string {\n  if (!federalTaxNumber || federalTaxNumber.trim() === '') {\n    throw new ValidationError('Federal tax number (CPF) is required');\n  }\n\n  const normalized = normalizeCpf(federalTaxNumber);\n\n  if (normalized.length !== 11) {\n    throw new ValidationError(\n      `Invalid federal tax number format: \"${federalTaxNumber}\". Expected 11 digits (e.g., \"12345678901\" or \"123.456.789-01\"), got ${normalized.length} digit(s).`\n    );\n  }\n\n  return normalized;\n}\n\n/**\n * Validates and normalizes a birth date parameter.\n * Accepts a string in YYYY-MM-DD format or a Date object.\n *\n * @param birthDate - Birth date as string (YYYY-MM-DD) or Date object\n * @returns Normalized YYYY-MM-DD string\n * @throws {ValidationError} If input is empty, invalid format, or invalid date values\n */\nfunction validateBirthDate(birthDate: string | Date | undefined | null): string {\n  if (birthDate === undefined || birthDate === null) {\n    throw new ValidationError('Birth date is required');\n  }\n\n  // Convert Date object to YYYY-MM-DD string using UTC\n  if (birthDate instanceof Date) {\n    if (isNaN(birthDate.getTime())) {\n      throw new ValidationError('Birth date is an invalid Date object');\n    }\n    const year = birthDate.getUTCFullYear();\n    const month = String(birthDate.getUTCMonth() + 1).padStart(2, '0');\n    const day = String(birthDate.getUTCDate()).padStart(2, '0');\n    return `${year}-${month}-${day}`;\n  }\n\n  // Validate string format\n  if (typeof birthDate === 'string') {\n    if (birthDate.trim() === '') {\n      throw new ValidationError('Birth date is required');\n    }\n\n    const match = birthDate.match(/^(\\d{4})-(\\d{2})-(\\d{2})$/);\n    if (!match) {\n      throw new ValidationError(\n        `Invalid birth date format: \"${birthDate}\". Expected YYYY-MM-DD format (e.g., \"1990-01-15\").`\n      );\n    }\n\n    const monthStr = match[2] as string;\n    const dayStr = match[3] as string;\n    const month = parseInt(monthStr, 10);\n    const day = parseInt(dayStr, 10);\n\n    if (month < 1 || month > 12) {\n      throw new ValidationError(\n        `Invalid birth date: \"${birthDate}\". Month must be between 01 and 12, got ${monthStr}.`\n      );\n    }\n\n    if (day < 1 || day > 31) {\n      throw new ValidationError(\n        `Invalid birth date: \"${birthDate}\". Day must be between 01 and 31, got ${dayStr}.`\n      );\n    }\n\n    return birthDate;\n  }\n\n  throw new ValidationError('Birth date must be a string (YYYY-MM-DD) or a Date object');\n}\n\n// ============================================================================\n// Natural Person Lookup Resource\n// ============================================================================\n\n/**\n * Natural Person Lookup API Resource\n *\n * @description\n * Provides a read-only operation for querying CPF cadastral status (situação cadastral)\n * at the Brazilian Federal Revenue Service (Receita Federal) via the NFE.io Natural Person API.\n *\n * **Note:** This resource uses a different API host (naturalperson.api.nfe.io)\n * and may require a separate API key configured via `dataApiKey` in the client configuration.\n *\n * @example CPF cadastral status lookup\n * ```typescript\n * const result = await nfe.naturalPersonLookup.getStatus('123.456.789-01', '1990-01-15');\n * console.log(result.name);    // 'JOÃO DA SILVA'\n * console.log(result.status);  // 'Regular'\n * ```\n *\n * @example Using a Date object for birth date\n * ```typescript\n * const result = await nfe.naturalPersonLookup.getStatus('12345678901', new Date(1990, 0, 15));\n * console.log(result.status);  // 'Regular'\n * ```\n */\nexport class NaturalPersonLookupResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Public Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Lookup CPF cadastral status at Receita Federal\n   *\n   * @description\n   * Queries the cadastral status of a CPF (pessoa física) at the Brazilian Federal\n   * Revenue Service. Returns the person's name, CPF, birth date, cadastral status\n   * (Regular, Suspensa, Cancelada, etc.), and query timestamp.\n   *\n   * @param federalTaxNumber - CPF number, with or without punctuation (e.g., \"12345678901\" or \"123.456.789-01\")\n   * @param birthDate - Date of birth as string in YYYY-MM-DD format (e.g., \"1990-01-15\") or a Date object\n   * @returns Promise with the CPF cadastral status response\n   * @throws {ValidationError} If CPF format is invalid (not 11 digits) or birth date format is invalid\n   * @throws {NotFoundError} If CPF is not found or birth date does not match (404)\n   * @throws {AuthenticationError} If API key is invalid or missing (401)\n   *\n   * @example\n   * ```typescript\n   * // Simple lookup with string date\n   * const result = await nfe.naturalPersonLookup.getStatus('12345678901', '1990-01-15');\n   * console.log(result.name);    // 'JOÃO DA SILVA'\n   * console.log(result.status);  // 'Regular'\n   *\n   * // With formatted CPF\n   * const result = await nfe.naturalPersonLookup.getStatus('123.456.789-01', '1990-01-15');\n   *\n   * // Using a Date object\n   * const result = await nfe.naturalPersonLookup.getStatus('12345678901', new Date(1990, 0, 15));\n   * ```\n   */\n  async getStatus(\n    federalTaxNumber: string,\n    birthDate: string | Date\n  ): Promise<NaturalPersonStatusResponse> {\n    const normalizedCpf = validateCpf(federalTaxNumber);\n    const normalizedDate = validateBirthDate(birthDate);\n\n    const response = await this.http.get<NaturalPersonStatusResponse>(\n      `/v1/naturalperson/status/${normalizedCpf}/${normalizedDate}`\n    );\n\n    return response.data;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Creates a NaturalPersonLookupResource instance\n *\n * @param http - HTTP client configured for the Natural Person API\n * @returns NaturalPersonLookupResource instance\n */\nexport function createNaturalPersonLookupResource(http: HttpClient): NaturalPersonLookupResource {\n  return new NaturalPersonLookupResource(http);\n}\n","/**\n * NFE.io SDK v3 - Tax Calculation Resource\n *\n * Provides access to the Motor de Cálculo de Tributos (Tax Calculation Engine),\n * which computes all applicable Brazilian taxes (ICMS, ICMS-ST, PIS, COFINS,\n * IPI, II) for product operations based on fiscal context.\n *\n * Uses the API host: api.nfse.io\n *\n * @see https://nfe.io/docs/nota-fiscal-eletronica/motor-de-calculo-de-imposto/\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type { CalculateRequest, CalculateResponse } from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Validates that tenantId is a non-empty string.\n * @param tenantId - The tenant/subscription ID to validate\n * @throws {ValidationError} If tenantId is empty or not a string\n */\nfunction validateTenantId(tenantId: string): void {\n  if (!tenantId || typeof tenantId !== 'string' || tenantId.trim() === '') {\n    throw new ValidationError('tenantId is required and must be a non-empty string');\n  }\n}\n\n/**\n * Validates required fields on a CalculateRequest.\n * @param request - The request payload to validate\n * @throws {ValidationError} If required fields are missing or invalid\n */\nfunction validateCalculateRequest(request: CalculateRequest): void {\n  if (!request) {\n    throw new ValidationError('request is required');\n  }\n\n  if (!request.issuer) {\n    throw new ValidationError('request.issuer is required');\n  }\n\n  if (!request.recipient) {\n    throw new ValidationError('request.recipient is required');\n  }\n\n  if (!request.operationType) {\n    throw new ValidationError('request.operationType is required');\n  }\n\n  if (!request.items || !Array.isArray(request.items) || request.items.length === 0) {\n    throw new ValidationError('request.items is required and must be a non-empty array');\n  }\n}\n\n// ============================================================================\n// Resource Implementation\n// ============================================================================\n\n/**\n * Tax Calculation Resource\n *\n * @description\n * Provides access to the NFE.io Tax Calculation Engine (Motor de Cálculo de\n * Tributos). The engine computes all applicable Brazilian taxes for product\n * operations, returning per-item tax breakdowns including CFOP determination.\n *\n * **Supported taxes:**\n * - ICMS (including ICMS-ST and FCP)\n * - ICMS interestadual (DIFAL / UF destination)\n * - PIS\n * - COFINS\n * - IPI\n * - II (Import Tax)\n *\n * **Authentication:** Uses data API key (`dataApiKey` or `apiKey` fallback)\n * via the CTE HTTP client (`api.nfse.io`).\n *\n * @example\n * ```typescript\n * const result = await nfe.taxCalculation.calculate('my-tenant-id', {\n *   operationType: 'Outgoing',\n *   issuer: { state: 'SP', taxRegime: 'RealProfit' },\n *   recipient: { state: 'RJ' },\n *   items: [{\n *     id: '1',\n *     operationCode: 121,\n *     origin: 'National',\n *     quantity: 10,\n *     unitAmount: 100.00,\n *     ncm: '61091000'\n *   }]\n * });\n *\n * for (const item of result.items ?? []) {\n *   console.log(`Item ${item.id}: CFOP ${item.cfop}`);\n *   console.log(`  ICMS CST: ${item.icms?.cst}, value: ${item.icms?.vICMS}`);\n *   console.log(`  PIS CST: ${item.pis?.cst}, value: ${item.pis?.vPIS}`);\n * }\n * ```\n */\nexport class TaxCalculationResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Public Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Calculate taxes for a product operation\n   *\n   * @description\n   * Submits an operation with issuer, recipient, operation type, and product items\n   * to the Tax Calculation Engine. Returns per-item tax breakdowns including all\n   * applicable Brazilian taxes (ICMS, PIS, COFINS, IPI, II) with CFOP determination.\n   *\n   * The `tenantId` is the subscription/account identifier that scopes the tax rules.\n   *\n   * @param tenantId - Subscription/account ID (required, non-empty)\n   * @param request - Tax calculation request with issuer, recipient, operation type, and items\n   * @returns Tax calculation response with per-item breakdowns\n   * @throws {ValidationError} If tenantId is empty\n   * @throws {ValidationError} If required request fields are missing (issuer, recipient, operationType, items)\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   * @throws {BadRequestError} If the API rejects the payload (HTTP 400)\n   * @throws {ValidationError} If the API returns unprocessable content (HTTP 422)\n   *\n   * @example Basic calculation\n   * ```typescript\n   * const result = await nfe.taxCalculation.calculate('tenant-123', {\n   *   operationType: 'Outgoing',\n   *   issuer: { state: 'SP', taxRegime: 'RealProfit' },\n   *   recipient: { state: 'RJ' },\n   *   items: [{\n   *     id: 'item-1',\n   *     operationCode: 121,\n   *     origin: 'National',\n   *     quantity: 1,\n   *     unitAmount: 500.00,\n   *     ncm: '61091000'\n   *   }]\n   * });\n   * console.log(result.items?.[0]?.cfop); // e.g., 6102\n   * ```\n   *\n   * @example With per-item tax profiles\n   * ```typescript\n   * const result = await nfe.taxCalculation.calculate('tenant-123', {\n   *   operationType: 'Incoming',\n   *   issuer: { state: 'MG', taxRegime: 'NationalSimple' },\n   *   recipient: { state: 'SP', taxRegime: 'RealProfit' },\n   *   items: [{\n   *     id: 'item-1',\n   *     operationCode: 569,\n   *     acquisitionPurpose: '569',\n   *     origin: 'National',\n   *     quantity: 100,\n   *     unitAmount: 25.50,\n   *     ncm: '39174090',\n   *     issuerTaxProfile: 'industry',\n   *     recipientTaxProfile: 'industry'\n   *   }]\n   * });\n   * ```\n   */\n  async calculate(tenantId: string, request: CalculateRequest): Promise<CalculateResponse> {\n    validateTenantId(tenantId);\n    validateCalculateRequest(request);\n\n    const response = await this.http.post<CalculateResponse>(\n      `/tax-rules/${encodeURIComponent(tenantId.trim())}/engine/calculate`,\n      request\n    );\n    return response.data;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Create a new TaxCalculationResource instance\n */\nexport function createTaxCalculationResource(http: HttpClient): TaxCalculationResource {\n  return new TaxCalculationResource(http);\n}\n","/**\n * NFE.io SDK v3 - Tax Codes Resource\n *\n * Provides paginated listings of auxiliary tax code reference tables\n * needed as inputs for tax calculation: operation codes, acquisition\n * purposes, issuer tax profiles, and recipient tax profiles.\n *\n * Uses the API host: api.nfse.io\n *\n * @see https://nfe.io/docs/nota-fiscal-eletronica/motor-de-calculo-de-imposto/\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type { TaxCodePaginatedResponse, TaxCodeListOptions } from '../types.js';\n\n// ============================================================================\n// Helpers\n// ============================================================================\n\n/**\n * Build query string from pagination options.\n * @param options - Optional pagination parameters\n * @returns Query string (including leading '?') or empty string\n */\nfunction buildPaginationQuery(options?: TaxCodeListOptions): string {\n  if (!options) return '';\n\n  const params = new URLSearchParams();\n\n  if (options.pageIndex !== undefined && options.pageIndex !== null) {\n    params.set('pageIndex', String(options.pageIndex));\n  }\n  if (options.pageCount !== undefined && options.pageCount !== null) {\n    params.set('pageCount', String(options.pageCount));\n  }\n\n  const qs = params.toString();\n  return qs ? `?${qs}` : '';\n}\n\n// ============================================================================\n// Resource Implementation\n// ============================================================================\n\n/**\n * Tax Codes Resource\n *\n * @description\n * Provides paginated listings of the four auxiliary reference tables used as\n * inputs for the Tax Calculation Engine:\n *\n * - **Operation Codes** — natureza de operação (e.g., 121 = \"Venda de mercadoria\")\n * - **Acquisition Purposes** — finalidade de aquisição (e.g., 569 = \"Compra para comercialização\")\n * - **Issuer Tax Profiles** — perfil fiscal do emissor (e.g., \"retail\", \"industry\")\n * - **Recipient Tax Profiles** — perfil fiscal do destinatário (e.g., \"final_consumer_non_icms_contributor\")\n *\n * All methods support pagination via `pageIndex` (1-based) and `pageCount` parameters.\n *\n * **Authentication:** Uses data API key (`dataApiKey` or `apiKey` fallback)\n * via the CTE HTTP client (`api.nfse.io`).\n *\n * @example\n * ```typescript\n * // List operation codes (first page)\n * const codes = await nfe.taxCodes.listOperationCodes();\n * for (const code of codes.items ?? []) {\n *   console.log(`${code.code} - ${code.description}`);\n * }\n *\n * // With pagination\n * const page2 = await nfe.taxCodes.listOperationCodes({ pageIndex: 2, pageCount: 20 });\n * console.log(`Page ${page2.currentPage} of ${page2.totalPages}`);\n * ```\n */\nexport class TaxCodesResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  // --------------------------------------------------------------------------\n  // Public Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * List operation codes (natureza de operação)\n   *\n   * @description\n   * Returns a paginated list of operation codes used in the `operationCode` field\n   * of tax calculation item requests. Each code represents a specific operation\n   * nature (e.g., sale, return, transfer).\n   *\n   * @param options - Optional pagination parameters\n   * @returns Paginated list of operation codes\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.taxCodes.listOperationCodes();\n   * console.log(`Total: ${result.totalCount} codes`);\n   * for (const code of result.items ?? []) {\n   *   console.log(`${code.code} - ${code.description}`);\n   * }\n   * ```\n   *\n   * @example With pagination\n   * ```typescript\n   * const page = await nfe.taxCodes.listOperationCodes({ pageIndex: 2, pageCount: 10 });\n   * console.log(`Page ${page.currentPage} of ${page.totalPages}`);\n   * ```\n   */\n  async listOperationCodes(options?: TaxCodeListOptions): Promise<TaxCodePaginatedResponse> {\n    const qs = buildPaginationQuery(options);\n    const response = await this.http.get<TaxCodePaginatedResponse>(\n      `/tax-codes/operation-code${qs}`\n    );\n    return response.data;\n  }\n\n  /**\n   * List acquisition purposes (finalidade de aquisição)\n   *\n   * @description\n   * Returns a paginated list of acquisition purpose codes used in the\n   * `acquisitionPurpose` field of tax calculation item requests.\n   *\n   * @param options - Optional pagination parameters\n   * @returns Paginated list of acquisition purposes\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.taxCodes.listAcquisitionPurposes();\n   * for (const purpose of result.items ?? []) {\n   *   console.log(`${purpose.code} - ${purpose.description}`);\n   * }\n   * ```\n   */\n  async listAcquisitionPurposes(options?: TaxCodeListOptions): Promise<TaxCodePaginatedResponse> {\n    const qs = buildPaginationQuery(options);\n    const response = await this.http.get<TaxCodePaginatedResponse>(\n      `/tax-codes/acquisition-purpose${qs}`\n    );\n    return response.data;\n  }\n\n  /**\n   * List issuer tax profiles (perfil fiscal do emissor)\n   *\n   * @description\n   * Returns a paginated list of issuer tax profile codes used in the\n   * `issuerTaxProfile` field of tax calculation item requests or the\n   * `taxProfile` field of the issuer.\n   *\n   * @param options - Optional pagination parameters\n   * @returns Paginated list of issuer tax profiles\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.taxCodes.listIssuerTaxProfiles();\n   * for (const profile of result.items ?? []) {\n   *   console.log(`${profile.code} - ${profile.description}`);\n   * }\n   * ```\n   */\n  async listIssuerTaxProfiles(options?: TaxCodeListOptions): Promise<TaxCodePaginatedResponse> {\n    const qs = buildPaginationQuery(options);\n    const response = await this.http.get<TaxCodePaginatedResponse>(\n      `/tax-codes/issuer-tax-profile${qs}`\n    );\n    return response.data;\n  }\n\n  /**\n   * List recipient tax profiles (perfil fiscal do destinatário)\n   *\n   * @description\n   * Returns a paginated list of recipient tax profile codes used in the\n   * `recipientTaxProfile` field of tax calculation item requests or the\n   * `taxProfile` field of the recipient.\n   *\n   * @param options - Optional pagination parameters\n   * @returns Paginated list of recipient tax profiles\n   * @throws {AuthenticationError} If API key is invalid (HTTP 401)\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.taxCodes.listRecipientTaxProfiles();\n   * for (const profile of result.items ?? []) {\n   *   console.log(`${profile.code} - ${profile.description}`);\n   * }\n   * ```\n   */\n  async listRecipientTaxProfiles(options?: TaxCodeListOptions): Promise<TaxCodePaginatedResponse> {\n    const qs = buildPaginationQuery(options);\n    const response = await this.http.get<TaxCodePaginatedResponse>(\n      `/tax-codes/recipient-tax-profile${qs}`\n    );\n    return response.data;\n  }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Create a new TaxCodesResource instance\n */\nexport function createTaxCodesResource(http: HttpClient): TaxCodesResource {\n  return new TaxCodesResource(http);\n}\n","/**\n * NFE.io SDK v3 - Product Invoices Resource (NF-e Issuance)\n *\n * Handles NF-e (Nota Fiscal Eletrônica de Produto) issuance operations via the v2 API.\n * Uses api.nfse.io host (same as transportation/inbound resources).\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  NfeProductInvoiceIssueData,\n  NfeProductInvoice,\n  NfeProductInvoiceListOptions,\n  NfeProductInvoiceListResponse,\n  NfeProductInvoiceSubListOptions,\n  NfeInvoiceItemsResponse,\n  NfeProductInvoiceEventsResponse,\n  NfeFileResource,\n  NfeRequestCancellationResource,\n  NfeDisablementData,\n  NfeDisablementResource,\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\nfunction validateInvoiceId(invoiceId: string): void {\n  if (!invoiceId || invoiceId.trim() === '') {\n    throw new ValidationError('Invoice ID is required');\n  }\n}\n\nfunction validateStateTaxId(stateTaxId: string): void {\n  if (!stateTaxId || stateTaxId.trim() === '') {\n    throw new ValidationError('State tax ID is required');\n  }\n}\n\nfunction buildQueryString(params: Record<string, string | number | boolean>): string {\n  const parts: string[] = [];\n  for (const [key, value] of Object.entries(params)) {\n    if (value !== undefined && value !== null) {\n      parts.push(`${encodeURIComponent(key)}=${encodeURIComponent(String(value))}`);\n    }\n  }\n  return parts.length > 0 ? `?${parts.join('&')}` : '';\n}\n\n// ============================================================================\n// Product Invoices Resource\n// ============================================================================\n\n/**\n * Product Invoices (NF-e) API Resource\n *\n * @description\n * Provides full lifecycle management for NF-e (Nota Fiscal Eletronica de Produto)\n * product invoices -- issue, list, retrieve, cancel, send correction letters (CC-e),\n * disable invoice numbers, and download files (PDF/XML).\n *\n * All operations are scoped by company and use the api.nfse.io v2 API.\n *\n * **Important:** Issue, cancel, correction letter, and disablement operations are\n * asynchronous -- they return 202/204 indicating the request was enqueued.\n * Completion is notified via webhooks.\n *\n * **Prerequisites:**\n * - Company must be registered with a valid A1 digital certificate\n * - State tax registration (Inscricao Estadual) must be configured\n *\n * @example Issue a product invoice\n * \\`\\`\\`typescript\n * const result = await nfe.productInvoices.create('company-id', {\n *   operationNature: 'Venda de mercadoria',\n *   operationType: 'Outgoing',\n *   buyer: { name: 'Empresa LTDA', federalTaxNumber: 12345678000190 },\n *   items: [{ code: 'PROD-001', description: 'Produto X', quantity: 1, unitAmount: 100 }],\n *   payment: [{ paymentDetail: [{ method: 'Cash', amount: 100 }] }],\n * });\n * \\`\\`\\`\n */\nexport class ProductInvoicesResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  private basePath(companyId: string): string {\n    return `/v2/companies/${companyId}/productinvoices`;\n  }\n\n  // --------------------------------------------------------------------------\n  // Issue (Create)\n  // --------------------------------------------------------------------------\n\n  /**\n   * Issue a product invoice (NF-e) by posting it to the processing queue.\n   *\n   * Processing is asynchronous -- a 202 response indicates the invoice was enqueued.\n   * Monitor completion via webhooks.\n   *\n   * @param companyId - The company ID\n   * @param data - Invoice issue data (buyer, items, payment, operationNature, etc.)\n   * @returns The enqueued invoice data\n   * @throws {ValidationError} If companyId is empty\n   * @throws {BadRequestError} If invoice data is invalid\n   */\n  async create(\n    companyId: string,\n    data: NfeProductInvoiceIssueData,\n  ): Promise<NfeProductInvoiceIssueData> {\n    validateCompanyId(companyId);\n    const response = await this.http.post<NfeProductInvoiceIssueData>(\n      this.basePath(companyId),\n      data,\n    );\n    return response.data;\n  }\n\n  /**\n   * Issue a product invoice (NF-e) specifying a particular state tax registration.\n   *\n   * Processing is asynchronous -- a 202 response indicates the invoice was enqueued.\n   *\n   * @param companyId - The company ID\n   * @param stateTaxId - The state tax registration ID (Inscricao Estadual)\n   * @param data - Invoice issue data\n   * @returns The enqueued invoice data\n   * @throws {ValidationError} If companyId or stateTaxId is empty\n   */\n  async createWithStateTax(\n    companyId: string,\n    stateTaxId: string,\n    data: NfeProductInvoiceIssueData,\n  ): Promise<NfeProductInvoiceIssueData> {\n    validateCompanyId(companyId);\n    validateStateTaxId(stateTaxId);\n    const response = await this.http.post<NfeProductInvoiceIssueData>(\n      `/v2/companies/${companyId}/statetaxes/${stateTaxId}/productinvoices`,\n      data,\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // List & Retrieve\n  // --------------------------------------------------------------------------\n\n  /**\n   * List product invoices (NF-e) for a company with cursor-based pagination.\n   *\n   * The environment option is required.\n   *\n   * @param companyId - The company ID\n   * @param options - List options (environment required, pagination, ElasticSearch query)\n   * @returns Paginated list of invoices\n   * @throws {ValidationError} If companyId is empty or environment is missing\n   */\n  async list(\n    companyId: string,\n    options: NfeProductInvoiceListOptions,\n  ): Promise<NfeProductInvoiceListResponse> {\n    validateCompanyId(companyId);\n    if (!options?.environment) {\n      throw new ValidationError('Environment is required (Production or Test)');\n    }\n    const params: Record<string, unknown> = {\n      environment: options.environment,\n    };\n    if (options.startingAfter !== undefined) params.startingAfter = options.startingAfter;\n    if (options.endingBefore !== undefined) params.endingBefore = options.endingBefore;\n    if (options.limit !== undefined) params.limit = options.limit;\n    if (options.q !== undefined) params.q = options.q;\n\n    const response = await this.http.get<NfeProductInvoiceListResponse>(\n      this.basePath(companyId),\n      params,\n    );\n    return response.data;\n  }\n\n  /**\n   * Retrieve a single product invoice (NF-e) by ID.\n   *\n   * Returns full invoice details including authorization, buyer, totals,\n   * transport, billing, payment, and last events.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @returns Full invoice details\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   * @throws {NotFoundError} If invoice does not exist\n   */\n  async retrieve(\n    companyId: string,\n    invoiceId: string,\n  ): Promise<NfeProductInvoice> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<NfeProductInvoice>(\n      `${this.basePath(companyId)}/${invoiceId}`,\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Cancel\n  // --------------------------------------------------------------------------\n\n  /**\n   * Cancel a product invoice (NF-e) by enqueuing it for cancellation.\n   *\n   * Processing is asynchronous -- a 204 response indicates the request was enqueued.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID to cancel\n   * @param reason - Optional reason for cancellation\n   * @returns Cancellation request details\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   * @throws {NotFoundError} If invoice does not exist\n   */\n  async cancel(\n    companyId: string,\n    invoiceId: string,\n    reason?: string,\n  ): Promise<NfeRequestCancellationResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const params: Record<string, string> = {};\n    if (reason !== undefined) params.reason = reason;\n    const qs = buildQueryString(params);\n    const response = await this.http.delete<NfeRequestCancellationResource>(\n      `${this.basePath(companyId)}/${invoiceId}${qs}`,\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Items & Events\n  // --------------------------------------------------------------------------\n\n  /**\n   * List items (products/services) for a specific invoice.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @param options - Optional pagination (limit, startingAfter)\n   * @returns Paginated list of invoice items\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   * @throws {NotFoundError} If invoice does not exist\n   */\n  async listItems(\n    companyId: string,\n    invoiceId: string,\n    options?: NfeProductInvoiceSubListOptions,\n  ): Promise<NfeInvoiceItemsResponse> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const params: Record<string, unknown> = {};\n    if (options?.limit !== undefined) params.limit = options.limit;\n    if (options?.startingAfter !== undefined) params.startingAfter = options.startingAfter;\n    const response = await this.http.get<NfeInvoiceItemsResponse>(\n      `${this.basePath(companyId)}/${invoiceId}/items`,\n      params,\n    );\n    return response.data;\n  }\n\n  /**\n   * List fiscal events for a specific invoice.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @param options - Optional pagination (limit, startingAfter)\n   * @returns Paginated list of invoice events\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   */\n  async listEvents(\n    companyId: string,\n    invoiceId: string,\n    options?: NfeProductInvoiceSubListOptions,\n  ): Promise<NfeProductInvoiceEventsResponse> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const params: Record<string, unknown> = {};\n    if (options?.limit !== undefined) params.limit = options.limit;\n    if (options?.startingAfter !== undefined) params.startingAfter = options.startingAfter;\n    const response = await this.http.get<NfeProductInvoiceEventsResponse>(\n      `${this.basePath(companyId)}/${invoiceId}/events`,\n      params,\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // File Downloads (PDF / XML)\n  // --------------------------------------------------------------------------\n\n  /**\n   * Get the URL for the DANFE PDF file of an invoice.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @param force - If true, forces PDF regeneration regardless of FlowStatus\n   * @returns File resource with URI to the PDF\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   */\n  async downloadPdf(\n    companyId: string,\n    invoiceId: string,\n    force?: boolean,\n  ): Promise<NfeFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const params: Record<string, unknown> = {};\n    if (force !== undefined) params.force = force;\n    const response = await this.http.get<NfeFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/pdf`,\n      params,\n    );\n    return response.data;\n  }\n\n  /**\n   * Get the URL for the authorized NF-e XML file.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @returns File resource with URI to the XML\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   */\n  async downloadXml(\n    companyId: string,\n    invoiceId: string,\n  ): Promise<NfeFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<NfeFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/xml`,\n    );\n    return response.data;\n  }\n\n  /**\n   * Get the URL for the NF-e rejection XML file.\n   *\n   * Uses the /xml-rejection endpoint (canonical form).\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @returns File resource with URI to the rejection XML\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   */\n  async downloadRejectionXml(\n    companyId: string,\n    invoiceId: string,\n  ): Promise<NfeFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<NfeFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/xml-rejection`,\n    );\n    return response.data;\n  }\n\n  /**\n   * Get the URL for the contingency authorization (EPEC) XML file.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @returns File resource with URI to the EPEC XML\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   */\n  async downloadEpecXml(\n    companyId: string,\n    invoiceId: string,\n  ): Promise<NfeFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<NfeFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/xml-epec`,\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Correction Letter (CC-e)\n  // --------------------------------------------------------------------------\n\n  /**\n   * Send a correction letter (Carta de Correcao - CC-e) for a product invoice.\n   *\n   * Processing is asynchronous. The reason text must contain between 15 and 1,000\n   * characters without accents or special characters.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @param reason - Correction reason (15-1,000 characters, no accents/special chars)\n   * @returns Cancellation request resource with operation details\n   * @throws {ValidationError} If reason is too short or too long\n   */\n  async sendCorrectionLetter(\n    companyId: string,\n    invoiceId: string,\n    reason: string,\n  ): Promise<NfeRequestCancellationResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    if (!reason || reason.length < 15) {\n      throw new ValidationError(\n        'Correction letter reason must contain at least 15 characters',\n      );\n    }\n    if (reason.length > 1000) {\n      throw new ValidationError(\n        'Correction letter reason must contain at most 1,000 characters',\n      );\n    }\n    const response = await this.http.put<NfeRequestCancellationResource>(\n      `${this.basePath(companyId)}/${invoiceId}/correctionletter`,\n      { reason },\n    );\n    return response.data;\n  }\n\n  /**\n   * Get the URL for the CC-e DANFE PDF file.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @returns File resource with URI to the correction letter PDF\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   */\n  async downloadCorrectionLetterPdf(\n    companyId: string,\n    invoiceId: string,\n  ): Promise<NfeFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<NfeFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/correctionletter/pdf`,\n    );\n    return response.data;\n  }\n\n  /**\n   * Get the URL for the CC-e XML file.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID\n   * @returns File resource with URI to the correction letter XML\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   */\n  async downloadCorrectionLetterXml(\n    companyId: string,\n    invoiceId: string,\n  ): Promise<NfeFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<NfeFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/correctionletter/xml`,\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Disablement (Inutilizacao)\n  // --------------------------------------------------------------------------\n\n  /**\n   * Disable (inutilizar) a specific product invoice by ID.\n   *\n   * Processing is asynchronous. The reason parameter is optional.\n   *\n   * @param companyId - The company ID\n   * @param invoiceId - The invoice ID to disable\n   * @param reason - Optional reason for disablement\n   * @returns Cancellation request resource\n   * @throws {ValidationError} If companyId or invoiceId is empty\n   */\n  async disable(\n    companyId: string,\n    invoiceId: string,\n    reason?: string,\n  ): Promise<NfeRequestCancellationResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const params: Record<string, string> = {};\n    if (reason !== undefined) params.reason = reason;\n    const qs = buildQueryString(params);\n    const response = await this.http.post<NfeRequestCancellationResource>(\n      `${this.basePath(companyId)}/${invoiceId}/disablement${qs}`,\n    );\n    return response.data;\n  }\n\n  /**\n   * Disable a range of invoice numbers for a company.\n   *\n   * If disabling a single number, set beginNumber and lastNumber to the same value.\n   *\n   * @param companyId - The company ID\n   * @param data - Disablement data (environment, serie, state, beginNumber, lastNumber, reason?)\n   * @returns Disablement resource with operation details\n   * @throws {ValidationError} If companyId is empty\n   */\n  async disableRange(\n    companyId: string,\n    data: NfeDisablementData,\n  ): Promise<NfeDisablementResource> {\n    validateCompanyId(companyId);\n    const response = await this.http.post<NfeDisablementResource>(\n      `${this.basePath(companyId)}/disablement`,\n      data,\n    );\n    return response.data;\n  }\n}\n","/**\n * NFE.io SDK v3 - State Taxes Resource (Inscrições Estaduais)\n *\n * Handles CRUD operations for company state tax registrations (Inscrições Estaduais)\n * via the api.nfse.io v2 API. State taxes define the series, numbering, environment,\n * and state code configuration required for NF-e issuance.\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  NfeStateTax,\n  NfeStateTaxCreateData,\n  NfeStateTaxUpdateData,\n  NfeStateTaxListResponse,\n  NfeStateTaxListOptions,\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n// ============================================================================\n// Validation Helpers\n// ============================================================================\n\n/**\n * Validates company ID is not empty.\n * @param companyId - The company ID to validate\n * @throws {ValidationError} If company ID is empty\n */\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\n/**\n * Validates state tax ID is not empty.\n * @param stateTaxId - The state tax ID to validate\n * @throws {ValidationError} If state tax ID is empty\n */\nfunction validateStateTaxId(stateTaxId: string): void {\n  if (!stateTaxId || stateTaxId.trim() === '') {\n    throw new ValidationError('State tax ID is required');\n  }\n}\n\n// ============================================================================\n// State Taxes Resource\n// ============================================================================\n\n/**\n * State Taxes (Inscrições Estaduais) API Resource\n *\n * @description\n * Provides CRUD operations for company state tax registrations.\n * State taxes define the series, numbering, environment, and state configuration\n * required for NF-e product invoice issuance.\n *\n * All operations are scoped by company and use the `api.nfse.io` v2 API.\n *\n * @example List state taxes\n * ```typescript\n * const result = await nfe.stateTaxes.list('company-id');\n * for (const tax of result.stateTaxes ?? []) {\n *   console.log(tax.code, tax.taxNumber, tax.status);\n * }\n * ```\n *\n * @example Create a state tax registration\n * ```typescript\n * const tax = await nfe.stateTaxes.create('company-id', {\n *   taxNumber: '123456789',\n *   serie: 1,\n *   number: 1,\n *   code: 'sP',\n *   environmentType: 'production',\n *   type: 'nFe',\n * });\n * console.log(tax.id);\n * ```\n *\n * @example Update and delete\n * ```typescript\n * await nfe.stateTaxes.update('company-id', 'state-tax-id', { serie: 2 });\n * await nfe.stateTaxes.delete('company-id', 'state-tax-id');\n * ```\n */\nexport class StateTaxesResource {\n  private readonly http: HttpClient;\n\n  constructor(http: HttpClient) {\n    this.http = http;\n  }\n\n  /**\n   * Returns the base path for state tax operations.\n   */\n  private basePath(companyId: string): string {\n    return `/v2/companies/${companyId}/statetaxes`;\n  }\n\n  // --------------------------------------------------------------------------\n  // List\n  // --------------------------------------------------------------------------\n\n  /**\n   * List all state tax registrations (Inscrições Estaduais) for a company.\n   *\n   * Uses cursor-based pagination with `startingAfter`, `endingBefore`, and `limit`.\n   *\n   * @param companyId - The company ID\n   * @param options - Optional pagination options\n   * @returns List of state tax registrations\n   * @throws {ValidationError} If companyId is empty\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.stateTaxes.list('company-id');\n   * for (const tax of result.stateTaxes ?? []) {\n   *   console.log(tax.id, tax.taxNumber, tax.serie, tax.status);\n   * }\n   * ```\n   */\n  async list(\n    companyId: string,\n    options?: NfeStateTaxListOptions,\n  ): Promise<NfeStateTaxListResponse> {\n    validateCompanyId(companyId);\n    const params: Record<string, unknown> = {};\n    if (options?.startingAfter !== undefined) params.startingAfter = options.startingAfter;\n    if (options?.endingBefore !== undefined) params.endingBefore = options.endingBefore;\n    if (options?.limit !== undefined) params.limit = options.limit;\n    const response = await this.http.get<NfeStateTaxListResponse>(\n      this.basePath(companyId),\n      params,\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Create\n  // --------------------------------------------------------------------------\n\n  /**\n   * Create a new state tax registration (Inscrição Estadual) for a company.\n   *\n   * @param companyId - The company ID\n   * @param data - State tax data (taxNumber, serie, and number are required)\n   * @returns The created state tax record\n   * @throws {ValidationError} If companyId is empty\n   * @throws {BadRequestError} If required fields are missing\n   *\n   * @example\n   * ```typescript\n   * const tax = await nfe.stateTaxes.create('company-id', {\n   *   taxNumber: '123456789',\n   *   serie: 1,\n   *   number: 1,\n   *   code: 'sP',\n   *   environmentType: 'production',\n   * });\n   * ```\n   */\n  async create(\n    companyId: string,\n    data: NfeStateTaxCreateData,\n  ): Promise<NfeStateTax> {\n    validateCompanyId(companyId);\n    const response = await this.http.post<NfeStateTax>(\n      this.basePath(companyId),\n      { stateTax: data },\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Retrieve\n  // --------------------------------------------------------------------------\n\n  /**\n   * Retrieve a specific state tax registration by ID.\n   *\n   * @param companyId - The company ID\n   * @param stateTaxId - The state tax ID\n   * @returns The state tax record\n   * @throws {ValidationError} If companyId or stateTaxId is empty\n   * @throws {NotFoundError} If state tax record does not exist\n   *\n   * @example\n   * ```typescript\n   * const tax = await nfe.stateTaxes.retrieve('company-id', 'state-tax-id');\n   * console.log(tax.taxNumber, tax.environmentType, tax.serie);\n   * ```\n   */\n  async retrieve(\n    companyId: string,\n    stateTaxId: string,\n  ): Promise<NfeStateTax> {\n    validateCompanyId(companyId);\n    validateStateTaxId(stateTaxId);\n    const response = await this.http.get<NfeStateTax>(\n      `${this.basePath(companyId)}/${stateTaxId}`,\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Update\n  // --------------------------------------------------------------------------\n\n  /**\n   * Update an existing state tax registration.\n   *\n   * @param companyId - The company ID\n   * @param stateTaxId - The state tax ID to update\n   * @param data - Fields to update\n   * @returns The updated state tax record\n   * @throws {ValidationError} If companyId or stateTaxId is empty\n   * @throws {NotFoundError} If state tax record does not exist\n   *\n   * @example\n   * ```typescript\n   * const tax = await nfe.stateTaxes.update('company-id', 'state-tax-id', {\n   *   serie: 2,\n   *   environmentType: 'test',\n   * });\n   * ```\n   */\n  async update(\n    companyId: string,\n    stateTaxId: string,\n    data: NfeStateTaxUpdateData,\n  ): Promise<NfeStateTax> {\n    validateCompanyId(companyId);\n    validateStateTaxId(stateTaxId);\n    const response = await this.http.put<NfeStateTax>(\n      `${this.basePath(companyId)}/${stateTaxId}`,\n      { stateTax: data },\n    );\n    return response.data;\n  }\n\n  // --------------------------------------------------------------------------\n  // Delete\n  // --------------------------------------------------------------------------\n\n  /**\n   * Delete a state tax registration.\n   *\n   * @param companyId - The company ID\n   * @param stateTaxId - The state tax ID to delete\n   * @throws {ValidationError} If companyId or stateTaxId is empty\n   * @throws {NotFoundError} If state tax record does not exist\n   *\n   * @example\n   * ```typescript\n   * await nfe.stateTaxes.delete('company-id', 'state-tax-id');\n   * ```\n   */\n  async delete(\n    companyId: string,\n    stateTaxId: string,\n  ): Promise<void> {\n    validateCompanyId(companyId);\n    validateStateTaxId(stateTaxId);\n    await this.http.delete(\n      `${this.basePath(companyId)}/${stateTaxId}`,\n    );\n  }\n\n  /**\n   * Switch the NF-e authorizer (SEFAZ environment/authorizer) for a state tax.\n   *\n   * @param companyId - The company ID\n   * @param stateTaxId - The state tax ID\n   * @param data - Optional switch payload (authorizer selection)\n   * @returns The updated state tax record\n   */\n  async switchAuthorizer(\n    companyId: string,\n    stateTaxId: string,\n    data?: Record<string, unknown>,\n  ): Promise<NfeStateTax> {\n    validateCompanyId(companyId);\n    validateStateTaxId(stateTaxId);\n    const response = await this.http.post<NfeStateTax>(\n      `${this.basePath(companyId)}/${stateTaxId}/switch-authorizer`,\n      data ?? {},\n    );\n    return response.data;\n  }\n}\n","/**\n * NFE.io SDK v4 - Service Invoices RTC Resource (NFS-e, Reforma Tributária)\n *\n * Emits NFS-e under the RTC layout (IBS/CBS groups) via the same endpoint as the\n * legacy service-invoices resource. RTC is selected by the payload shape\n * (`ibsCbs` group), not by a header or a different URL.\n *\n * Host: api.nfe.io (main client). The base URL already carries `/v1`, so paths\n * here MUST NOT prepend `/v1`.\n *\n * Async model: NFS-e supports polling (202 + Location -> poll until terminal),\n * mirroring the legacy service-invoices resource. Retrieve/cancel/PDF/XML of an\n * emitted invoice are shared with `nfe.serviceInvoices` (same invoice id space);\n * this resource adds RTC emission + the cancellation-event XML download.\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  ServiceInvoiceData,\n  NFSeRtcRequest,\n  PollingOptions,\n  FlowStatus,\n} from '../types.js';\nimport type { CreateInvoiceResponse } from './service-invoices.js';\nimport { InvoiceProcessingError, NotFoundError, ValidationError } from '../errors/index.js';\nimport { poll } from '../utils/polling.js';\nimport { isTerminalFlowStatus } from '../types.js';\n\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\nfunction validateInvoiceId(invoiceId: string): void {\n  if (!invoiceId || invoiceId.trim() === '') {\n    throw new ValidationError('Invoice ID is required');\n  }\n}\n\nexport class ServiceInvoicesRtcResource {\n  constructor(private readonly http: HttpClient) {}\n\n  /** No `/v1` prefix — the main client base URL (`https://api.nfe.io/v1`) carries it. */\n  private basePath(companyId: string): string {\n    return `/companies/${companyId}/serviceinvoices`;\n  }\n\n  /**\n   * Emit an NFS-e with the RTC layout (`ibsCbs` group).\n   *\n   * Returns a discriminated union: immediate (201) or async (202 + Location).\n   * Use {@link createAndWait} to poll until the invoice reaches a terminal state.\n   */\n  async create(\n    companyId: string,\n    data: NFSeRtcRequest\n  ): Promise<CreateInvoiceResponse> {\n    validateCompanyId(companyId);\n    const response = await this.http.post<ServiceInvoiceData>(this.basePath(companyId), data);\n\n    if (response.status === 202) {\n      const location = response.headers['location'] || response.headers['Location'];\n      if (!location) {\n        throw new InvoiceProcessingError(\n          'Async response (202) received but no Location header found',\n          { status: 202, headers: response.headers }\n        );\n      }\n      const fullPath = location.startsWith('http') ? new URL(location).pathname : location;\n      return {\n        status: 'async',\n        response: {\n          code: 202,\n          status: 'pending',\n          location: fullPath,\n          invoiceId: this.extractInvoiceIdFromLocation(location),\n        },\n      };\n    }\n\n    return { status: 'immediate', invoice: response.data };\n  }\n\n  /**\n   * Emit an RTC NFS-e and poll until it reaches a terminal flow status.\n   */\n  async createAndWait(\n    companyId: string,\n    data: NFSeRtcRequest,\n    options: PollingOptions = {}\n  ): Promise<ServiceInvoiceData> {\n    const createResult = await this.create(companyId, data);\n    if (createResult.status === 'immediate') {\n      return createResult.invoice;\n    }\n\n    const { invoiceId } = createResult.response;\n    const pollingConfig: import('../utils/polling.js').PollingOptions<ServiceInvoiceData> = {\n      fn: async () => this.retrieve(companyId, invoiceId),\n      isComplete: (invoice) => isTerminalFlowStatus(invoice.flowStatus as FlowStatus),\n      timeout: options.timeout ?? 120000,\n      initialDelay: options.initialDelay ?? 1000,\n      maxDelay: options.maxDelay ?? 10000,\n      backoffFactor: options.backoffFactor ?? 1.5,\n    };\n    if (options.onPoll) {\n      pollingConfig.onPoll = (attempt, result) =>\n        options.onPoll!(attempt, result.flowStatus as FlowStatus);\n    }\n\n    const invoice = await poll<ServiceInvoiceData>(pollingConfig);\n    const flowStatus = invoice.flowStatus as FlowStatus;\n    if (flowStatus === 'IssueFailed' || flowStatus === 'CancelFailed') {\n      throw new InvoiceProcessingError(\n        `Invoice processing failed with status: ${flowStatus}`,\n        { flowStatus, flowMessage: invoice.flowMessage, invoice }\n      );\n    }\n    return invoice;\n  }\n\n  /** Retrieve an emitted invoice (used for polling; shares the endpoint with serviceInvoices). */\n  async retrieve(companyId: string, invoiceId: string): Promise<ServiceInvoiceData> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<ServiceInvoiceData>(\n      `${this.basePath(companyId)}/${invoiceId}`\n    );\n    if (!response.data) {\n      throw new NotFoundError(`Invoice ${invoiceId} not found`, { companyId, invoiceId });\n    }\n    return response.data;\n  }\n\n  /**\n   * Download the XML of the cancellation event (Ambiente Nacional) for an NFS-e.\n   *\n   * @returns The cancellation-event XML as a Buffer.\n   * @throws {NotFoundError} If the invoice/cancellation XML is not found/not ready.\n   */\n  async downloadCancellationXml(companyId: string, invoiceId: string): Promise<Buffer> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<Buffer>(\n      `${this.basePath(companyId)}/${invoiceId}/cancellation-xml`,\n      undefined,\n      { Accept: 'application/xml' }\n    );\n    return response.data;\n  }\n\n  private extractInvoiceIdFromLocation(location: string): string {\n    const path = location.split('?')[0]!.replace(/\\/+$/, '');\n    return path.split('/').pop() ?? '';\n  }\n}\n\nexport function createServiceInvoicesRtcResource(http: HttpClient): ServiceInvoicesRtcResource {\n  return new ServiceInvoicesRtcResource(http);\n}\n","/**\n * NFE.io SDK v4 - Product Invoices RTC Resource (NF-e/NFC-e, Reforma Tributária)\n *\n * Emits NF-e / NFC-e under the RTC layout (IBS state+municipal, CBS, IS groups)\n * via the same endpoint as the legacy product-invoices resource. RTC is selected\n * by the payload shape (`tax.IBSCBS`), not by a header or a different URL.\n *\n * Host: api.nfse.io (CT-e/data client). The base URL has no version segment, so\n * `/v2` belongs in the path.\n *\n * Async model: like the legacy product-invoices resource, emission is\n * **webhook-driven** — a 202 means the invoice was enqueued; completion is\n * notified via webhooks (NOT polled). Retrieve/cancel/PDF/XML are shared with\n * `nfe.productInvoices` (same invoice id space).\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type { NfeProductInvoiceIssueData, ProductInvoiceRtcRequest } from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\nexport class ProductInvoicesRtcResource {\n  constructor(private readonly http: HttpClient) {}\n\n  private basePath(companyId: string): string {\n    return `/v2/companies/${companyId}/productinvoices`;\n  }\n\n  /**\n   * Emit an NF-e / NFC-e with the RTC layout (item-level `tax.IBSCBS`).\n   *\n   * Webhook-driven: a 202 indicates the invoice was enqueued; monitor completion\n   * via webhooks. Returns the enqueued invoice data (does NOT poll).\n   */\n  async create(\n    companyId: string,\n    data: ProductInvoiceRtcRequest\n  ): Promise<NfeProductInvoiceIssueData> {\n    validateCompanyId(companyId);\n    const response = await this.http.post<NfeProductInvoiceIssueData>(\n      this.basePath(companyId),\n      data\n    );\n    return response.data;\n  }\n}\n\nexport function createProductInvoicesRtcResource(http: HttpClient): ProductInvoicesRtcResource {\n  return new ProductInvoicesRtcResource(http);\n}\n","/**\n * NFE.io SDK v4 - Municipal Taxes Resource (Inscrições Municipais)\n *\n * CRUD for company municipal tax registrations via the api.nfse.io v2 API,\n * mirroring StateTaxesResource. Municipal registration is a prerequisite for\n * NFS-e issuance in most municipalities. Adds `updateprefecture` (PATCH) and the\n * RPS `series` lookup. Types come from `contribuintes-v2` (sync change).\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  MunicipalTax,\n  CreateMunicipalTaxData,\n  UpdateMunicipalTaxData,\n  MunicipalTaxListResponse,\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\nimport { withUnservedRouteNote } from '../utils/unserved-route.js';\n\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\nfunction validateMunicipalTaxId(municipalTaxId: string): void {\n  if (!municipalTaxId || municipalTaxId.trim() === '') {\n    throw new ValidationError('Municipal tax ID is required');\n  }\n}\n\nexport class MunicipalTaxesResource {\n  constructor(private readonly http: HttpClient) {}\n\n  private basePath(companyId: string): string {\n    return `/v2/companies/${companyId}/municipaltaxes`;\n  }\n\n  /** List municipal tax registrations for a company. */\n  async list(companyId: string): Promise<MunicipalTaxListResponse> {\n    validateCompanyId(companyId);\n    const response = await this.http.get<MunicipalTaxListResponse>(this.basePath(companyId));\n    return response.data;\n  }\n\n  /** Create a municipal tax registration (wrapped as `{ municipalTax }`). */\n  async create(companyId: string, data: CreateMunicipalTaxData): Promise<MunicipalTax> {\n    validateCompanyId(companyId);\n    const response = await this.http.post<MunicipalTax>(this.basePath(companyId), {\n      municipalTax: data,\n    });\n    return response.data;\n  }\n\n  /** Retrieve a municipal tax registration by id. */\n  async retrieve(companyId: string, municipalTaxId: string): Promise<MunicipalTax> {\n    validateCompanyId(companyId);\n    validateMunicipalTaxId(municipalTaxId);\n    const response = await this.http.get<MunicipalTax>(\n      `${this.basePath(companyId)}/${municipalTaxId}`\n    );\n    return response.data;\n  }\n\n  /** Update a municipal tax registration. */\n  async update(\n    companyId: string,\n    municipalTaxId: string,\n    data: UpdateMunicipalTaxData\n  ): Promise<MunicipalTax> {\n    validateCompanyId(companyId);\n    validateMunicipalTaxId(municipalTaxId);\n    const response = await this.http.put<MunicipalTax>(\n      `${this.basePath(companyId)}/${municipalTaxId}`,\n      { municipalTax: data }\n    );\n    return response.data;\n  }\n\n  /** Delete a municipal tax registration. */\n  async delete(companyId: string, municipalTaxId: string): Promise<void> {\n    validateCompanyId(companyId);\n    validateMunicipalTaxId(municipalTaxId);\n    await this.http.delete(`${this.basePath(companyId)}/${municipalTaxId}`);\n  }\n\n  /**\n   * Update the prefecture (city hall) credentials/integration for a municipal tax\n   * registration. Uses HTTP PATCH (`.../updateprefecture`).\n   *\n   * @deprecated A plataforma **não serve** esta rota. Ela está declarada na spec\n   * `contribuintes-v2` e responde `404` — o mesmo `404` de corpo vazio que uma\n   * sub-rota inventada no mesmo host devolve (medido em 2026-09-02, com um\n   * `municipal_tax_id` cujo registro pai responde `200`). O método continua\n   * emitindo a requisição: se a rota subir, o resultado passa sem alteração.\n   */\n  async updatePrefecture(\n    companyId: string,\n    municipalTaxId: string,\n    data: UpdateMunicipalTaxData\n  ): Promise<MunicipalTax> {\n    validateCompanyId(companyId);\n    validateMunicipalTaxId(municipalTaxId);\n    const response = await withUnservedRouteNote(\n      'PATCH /v2/companies/{company_id}/municipaltaxes/{municipal_tax_id}/updateprefecture',\n      () =>\n        this.http.patch<MunicipalTax>(\n          `${this.basePath(companyId)}/${municipalTaxId}/updateprefecture`,\n          { municipalTax: data }\n        )\n    );\n    return response.data;\n  }\n\n  /**\n   * Look up an RPS series for a municipal tax registration.\n   *\n   * @deprecated A plataforma **não serve** esta rota — mesma medição de\n   * {@link MunicipalTaxesResource.updatePrefecture}. Testado com toda série\n   * plausível, inclusive a que o próprio registro declara em `rpsSerialNumber`:\n   * `404` de corpo vazio, sem `content-type`, idêntico ao de uma sub-rota\n   * inventada. O método continua emitindo a requisição.\n   */\n  async getSeries(\n    companyId: string,\n    municipalTaxId: string,\n    serie: string\n  ): Promise<Record<string, unknown>> {\n    validateCompanyId(companyId);\n    validateMunicipalTaxId(municipalTaxId);\n    if (!serie || serie.trim() === '') {\n      throw new ValidationError('Serie is required');\n    }\n    const response = await withUnservedRouteNote(\n      'GET /v2/companies/{company_id}/municipaltaxes/{municipal_tax_id}/series/{serie}',\n      () =>\n        this.http.get<Record<string, unknown>>(\n          `${this.basePath(companyId)}/${municipalTaxId}/series/${serie}`\n        )\n    );\n    return response.data;\n  }\n}\n\nexport function createMunicipalTaxesResource(http: HttpClient): MunicipalTaxesResource {\n  return new MunicipalTaxesResource(http);\n}\n","/**\n * NFE.io SDK v4 - Consumer Invoices Resource (NFC-e issuance)\n *\n * Company-scoped NFC-e lifecycle via the api.nfse.io v2 API. Distinct from the\n * read-only `ConsumerInvoiceQueryResource` (CFe-SAT coupon lookup) and from RTC\n * NFC-e (different payload). Emission is **webhook-driven** (202 = enqueued;\n * completion notified via webhooks), mirroring `product-invoices` (no polling).\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  ConsumerInvoiceData,\n  ConsumerInvoice,\n  ConsumerInvoiceListResponse,\n  ConsumerInvoiceDisablementData,\n  ConsumerInvoiceItemsResponse,\n  ConsumerInvoiceEventsResponse,\n  ConsumerInvoiceCancellationResponse,\n  ConsumerInvoiceFileResource,\n  NfeDisablementResource,\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\n/** The NFC-e API requires which environment's invoices to operate on. */\nexport type ConsumerInvoiceEnvironment = 'Production' | 'Test';\n\n/** Options for {@link ConsumerInvoicesResource.list}. `environment` is required by the API. */\nexport interface ConsumerInvoiceListOptions {\n  /** Required by the API (`Production` or `Test`). Omitting it yields HTTP 400. */\n  environment: ConsumerInvoiceEnvironment;\n  startingAfter?: string;\n  endingBefore?: string;\n  limit?: number;\n  /** Free-text query filter, if supported by the endpoint. */\n  q?: string;\n}\n\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\nfunction validateInvoiceId(invoiceId: string): void {\n  if (!invoiceId || invoiceId.trim() === '') {\n    throw new ValidationError('Invoice ID is required');\n  }\n}\n\n/**\n * Builds a query string from present values. Mirrors the local helper in\n * `product-invoices.ts` — `http.delete()` takes no params object, so the query\n * has to go in the path.\n */\nfunction buildQueryString(params: Record<string, string | number | boolean>): string {\n  const parts: string[] = [];\n  for (const [key, value] of Object.entries(params)) {\n    if (value !== undefined && value !== null) {\n      parts.push(`${encodeURIComponent(key)}=${encodeURIComponent(String(value))}`);\n    }\n  }\n  return parts.length > 0 ? `?${parts.join('&')}` : '';\n}\n\n/** Cursor pagination for the NFC-e sub-collections (items and events). */\nexport interface ConsumerInvoicePageOptions {\n  /** Page size. */\n  limit?: number;\n  /** Cursor: start after this index. */\n  startingAfter?: number;\n}\n\n/** Builds the query for the paginated sub-collections; omits absent values. */\nfunction buildPageParams(\n  options?: ConsumerInvoicePageOptions\n): Record<string, unknown> | undefined {\n  if (!options) return undefined;\n  const params: Record<string, unknown> = {};\n  if (options.limit !== undefined) params.limit = options.limit;\n  if (options.startingAfter !== undefined) params.startingAfter = options.startingAfter;\n  return Object.keys(params).length > 0 ? params : undefined;\n}\n\nexport class ConsumerInvoicesResource {\n  constructor(private readonly http: HttpClient) {}\n\n  private basePath(companyId: string): string {\n    return `/v2/companies/${companyId}/consumerinvoices`;\n  }\n\n  /**\n   * Emit an NFC-e (consumer invoice).\n   *\n   * Webhook-driven: a 202 indicates the invoice was enqueued; completion is\n   * notified via webhooks. Returns the enqueued invoice (does NOT poll).\n   */\n  async create(companyId: string, data: ConsumerInvoiceData): Promise<ConsumerInvoice> {\n    validateCompanyId(companyId);\n    const response = await this.http.post<ConsumerInvoice>(this.basePath(companyId), data);\n    return response.data;\n  }\n\n  /**\n   * List NFC-e for a company. The API **requires** `environment` (`Production` or\n   * `Test`); omitting it returns HTTP 400.\n   */\n  async list(\n    companyId: string,\n    options: ConsumerInvoiceListOptions\n  ): Promise<ConsumerInvoiceListResponse> {\n    validateCompanyId(companyId);\n    // A API EXIGE `environment` aqui: sem ele responde\n    // 400 {\"code\":40001,\"message\":\"environment has to be production or test\"}.\n    // A spec marca o parametro como opcional — a spec e que esta errada\n    // (verificado ao vivo em 2026-09-01). Este throw e a falha rapida equivalente.\n    if (!options?.environment) {\n      throw new ValidationError('Environment is required (Production or Test)');\n    }\n    const params: Record<string, unknown> = { environment: options.environment };\n    if (options.startingAfter) params.startingAfter = options.startingAfter;\n    if (options.endingBefore) params.endingBefore = options.endingBefore;\n    if (options.limit !== undefined) params.limit = options.limit;\n    if (options.q) params.q = options.q;\n    const response = await this.http.get<ConsumerInvoiceListResponse>(\n      this.basePath(companyId),\n      params\n    );\n    return response.data;\n  }\n\n  /**\n   * Retrieve an NFC-e by id.\n   *\n   * The route takes no query parameters — `environment` is neither required nor\n   * defined by the spec here (verified live 2026-09-01).\n   */\n  async retrieve(companyId: string, invoiceId: string): Promise<ConsumerInvoice> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<ConsumerInvoice>(\n      `${this.basePath(companyId)}/${invoiceId}`\n    );\n    return response.data;\n  }\n\n  /**\n   * Cancel an NFC-e.\n   *\n   * @param reason - Optional cancellation reason, sent as the `reason` query\n   *   parameter defined by the spec.\n   */\n  async cancel(\n    companyId: string,\n    invoiceId: string,\n    reason?: string\n  ): Promise<ConsumerInvoiceCancellationResponse> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const params: Record<string, string> = {};\n    if (reason !== undefined) params.reason = reason;\n    const response = await this.http.delete<ConsumerInvoiceCancellationResponse>(\n      `${this.basePath(companyId)}/${invoiceId}${buildQueryString(params)}`\n    );\n    return response.data;\n  }\n\n  /**\n   * List the items of an NFC-e, with cursor pagination (`limit`/`startingAfter`).\n   * The response carries `hasMore`.\n   */\n  async getItems(\n    companyId: string,\n    invoiceId: string,\n    options?: ConsumerInvoicePageOptions\n  ): Promise<ConsumerInvoiceItemsResponse> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<ConsumerInvoiceItemsResponse>(\n      `${this.basePath(companyId)}/${invoiceId}/items`,\n      buildPageParams(options)\n    );\n    return response.data;\n  }\n\n  /**\n   * List the events of an NFC-e, with cursor pagination (`limit`/`startingAfter`).\n   * The response carries `hasMore`.\n   */\n  async getEvents(\n    companyId: string,\n    invoiceId: string,\n    options?: ConsumerInvoicePageOptions\n  ): Promise<ConsumerInvoiceEventsResponse> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<ConsumerInvoiceEventsResponse>(\n      `${this.basePath(companyId)}/${invoiceId}/events`,\n      buildPageParams(options)\n    );\n    return response.data;\n  }\n\n  /**\n   * Get the DANFE-NFC-e PDF link.\n   *\n   * @param force - Force regeneration of the document (spec `force` query param).\n   *\n   * A API devolve `{ uri }` — URL temporaria para o arquivo, nao o binario. O\n   * header `Accept` nao altera a resposta. Verificado ao vivo em 2026-09-01\n   * (tests/fixtures/live-contracts/consumer-invoice-download.json).\n   *\n   * Atencao: o envelope difere das rotas de ENTRADA, que usam `publicTemporaryUri`.\n   */\n  async downloadPdf(\n    companyId: string,\n    invoiceId: string,\n    force?: boolean\n  ): Promise<ConsumerInvoiceFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<ConsumerInvoiceFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/pdf`,\n      force === undefined ? undefined : { force }\n    );\n    return response.data;\n  }\n\n  /**\n   * Get the NFC-e XML link.\n   *\n   * A API devolve `{ uri }` — URL temporaria para o arquivo, nao o binario. O\n   * header `Accept` nao altera a resposta. Verificado ao vivo em 2026-09-01\n   * (tests/fixtures/live-contracts/consumer-invoice-download.json).\n   *\n   * Atencao: o envelope difere das rotas de ENTRADA, que usam `publicTemporaryUri`.\n   */\n  async downloadXml(\n    companyId: string,\n    invoiceId: string\n  ): Promise<ConsumerInvoiceFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<ConsumerInvoiceFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/xml`\n    );\n    return response.data;\n  }\n\n  /**\n   * Get the rejection XML link for a rejected NFC-e.\n   *\n   * A API devolve `{ uri }` — URL temporaria para o arquivo, nao o binario. O\n   * header `Accept` nao altera a resposta. Verificado ao vivo em 2026-09-01\n   * (tests/fixtures/live-contracts/consumer-invoice-download.json).\n   *\n   * Atencao: o envelope difere das rotas de ENTRADA, que usam `publicTemporaryUri`.\n   */\n  async downloadRejectionXml(\n    companyId: string,\n    invoiceId: string\n  ): Promise<ConsumerInvoiceFileResource> {\n    validateCompanyId(companyId);\n    validateInvoiceId(invoiceId);\n    const response = await this.http.get<ConsumerInvoiceFileResource>(\n      `${this.basePath(companyId)}/${invoiceId}/xml/rejection`\n    );\n    return response.data;\n  }\n\n  /** Disable (inutilizar) a range of NFC-e numbers. */\n  async disable(\n    companyId: string,\n    data: ConsumerInvoiceDisablementData\n  ): Promise<NfeDisablementResource> {\n    validateCompanyId(companyId);\n    const response = await this.http.post<NfeDisablementResource>(\n      `${this.basePath(companyId)}/disablement`,\n      data\n    );\n    return response.data;\n  }\n}\n\nexport function createConsumerInvoicesResource(http: HttpClient): ConsumerInvoicesResource {\n  return new ConsumerInvoicesResource(http);\n}\n","/**\n * NFE.io SDK v4 - Certificates Resource (digital certificate management)\n *\n * Manages company digital certificates via the contribuintes-v2 (Empresas) API\n * on **api.nfse.io**. Covers the gap left by the legacy singular upload on\n * `companies` (which targets the api.nfe.io host): retrieve/delete by thumbprint\n * and the plural collection.\n *\n * Host note: this targets `api.nfse.io` (the contribuintes-v2 server). It is a\n * dedicated resource — NOT folded into `companies` — because `companies` is wired\n * to the api.nfe.io main client, a different host. Types come from contribuintes-v2.\n *\n * Validation note: `CertificateValidator` only pre-flights file format; the\n * certificate validity/password is verified server-side (see fix-repo-bugs).\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport type {\n  CertificateMetadataResource,\n  CertificatesMetadataResource,\n} from '../types.js';\nimport { ValidationError } from '../errors/index.js';\n\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\nfunction validateThumbprint(thumbprint: string): void {\n  if (!thumbprint || thumbprint.trim() === '') {\n    throw new ValidationError('Certificate thumbprint is required');\n  }\n}\n\nexport class CertificatesResource {\n  constructor(private readonly http: HttpClient) {}\n\n  private v2Base(companyId: string): string {\n    return `/v2/companies/${companyId}/certificates`;\n  }\n\n  private v1Base(companyId: string): string {\n    return `/v1/companies/${companyId}/certificate`;\n  }\n\n  /** List a company's certificates (`GET /v2/companies/{id}/certificates`). */\n  async list(companyId: string): Promise<CertificatesMetadataResource> {\n    validateCompanyId(companyId);\n    const response = await this.http.get<CertificatesMetadataResource>(this.v2Base(companyId));\n    return response.data;\n  }\n\n  /** Retrieve a certificate by thumbprint (`GET /v2/companies/{id}/certificates/{thumbprint}`). */\n  async getByThumbprint(\n    companyId: string,\n    thumbprint: string\n  ): Promise<CertificateMetadataResource> {\n    validateCompanyId(companyId);\n    validateThumbprint(thumbprint);\n    const response = await this.http.get<CertificateMetadataResource>(\n      `${this.v2Base(companyId)}/${thumbprint}`\n    );\n    return response.data;\n  }\n\n  /** Delete a certificate by thumbprint (`DELETE /v2/companies/{id}/certificates/{thumbprint}`). */\n  async deleteByThumbprint(companyId: string, thumbprint: string): Promise<void> {\n    validateCompanyId(companyId);\n    validateThumbprint(thumbprint);\n    await this.http.delete(`${this.v2Base(companyId)}/${thumbprint}`);\n  }\n\n  /** Retrieve a certificate by thumbprint via the v1 path (`/v1/companies/{id}/certificate/{thumbprint}`). */\n  async getByThumbprintV1(\n    companyId: string,\n    thumbprint: string\n  ): Promise<CertificateMetadataResource> {\n    validateCompanyId(companyId);\n    validateThumbprint(thumbprint);\n    const response = await this.http.get<CertificateMetadataResource>(\n      `${this.v1Base(companyId)}/${thumbprint}`\n    );\n    return response.data;\n  }\n\n  /** Delete a certificate by thumbprint via the v1 path. */\n  async deleteByThumbprintV1(companyId: string, thumbprint: string): Promise<void> {\n    validateCompanyId(companyId);\n    validateThumbprint(thumbprint);\n    await this.http.delete(`${this.v1Base(companyId)}/${thumbprint}`);\n  }\n}\n\nexport function createCertificatesResource(http: HttpClient): CertificatesResource {\n  return new CertificatesResource(http);\n}\n","/**\n * NFE.io SDK v4 - Notifications Resource (company notifications)\n *\n * Company-scoped notification operations on the main API (api.nfe.io). The\n * nf-servico-v1 spec has no component schemas for these, so types are minimal\n * hand types with a permissive index (consistent with the rest of that surface).\n */\n\nimport type { HttpClient } from '../http/client.js';\nimport { ValidationError } from '../errors/index.js';\n\n/** A company notification (minimal, spec has no named schema). */\nexport interface Notification {\n  id?: string;\n  [key: string]: unknown;\n}\n\n/** List response for notifications (best-effort shape). */\nexport interface NotificationListResponse {\n  notifications?: Notification[];\n  [key: string]: unknown;\n}\n\nfunction validateCompanyId(companyId: string): void {\n  if (!companyId || companyId.trim() === '') {\n    throw new ValidationError('Company ID is required');\n  }\n}\n\nfunction validateNotificationId(notificationId: string): void {\n  if (!notificationId || notificationId.trim() === '') {\n    throw new ValidationError('Notification ID is required');\n  }\n}\n\nexport class NotificationsResource {\n  constructor(private readonly http: HttpClient) {}\n\n  private basePath(companyId: string): string {\n    return `/companies/${companyId}/notifications`;\n  }\n\n  /** List company notifications. */\n  async list(companyId: string): Promise<NotificationListResponse> {\n    validateCompanyId(companyId);\n    const response = await this.http.get<NotificationListResponse>(this.basePath(companyId));\n    return response.data;\n  }\n\n  /** Retrieve a notification by id. */\n  async retrieve(companyId: string, notificationId: string): Promise<Notification> {\n    validateCompanyId(companyId);\n    validateNotificationId(notificationId);\n    const response = await this.http.get<Notification>(\n      `${this.basePath(companyId)}/${notificationId}`\n    );\n    return response.data;\n  }\n\n  /** Delete a notification. */\n  async delete(companyId: string, notificationId: string): Promise<void> {\n    validateCompanyId(companyId);\n    validateNotificationId(notificationId);\n    await this.http.delete(`${this.basePath(companyId)}/${notificationId}`);\n  }\n\n  /** Configure / send notification email settings. */\n  async sendEmail(companyId: string, data?: Record<string, unknown>): Promise<void> {\n    validateCompanyId(companyId);\n    await this.http.post(`${this.basePath(companyId)}/email`, data ?? {});\n  }\n}\n\nexport function createNotificationsResource(http: HttpClient): NotificationsResource {\n  return new NotificationsResource(http);\n}\n","/**\n * NFE.io SDK v3 - Resources Index\n *\n * Centralized exports for all API resources\n */\n\n// Resource classes\nexport { ServiceInvoicesResource, createServiceInvoicesResource } from './service-invoices.js';\nexport { CompaniesResource, createCompaniesResource } from './companies.js';\nexport type { CertificateStatusSummary } from './companies.js';\nexport { LegalPeopleResource } from './legal-people.js';\nexport { NaturalPeopleResource } from './natural-people.js';\nexport { WebhooksResource } from './webhooks.js';\nexport { AddressesResource, createAddressesResource, ADDRESS_API_BASE_URL } from './addresses.js';\nexport { TransportationInvoicesResource, createTransportationInvoicesResource, CTE_API_BASE_URL } from './transportation-invoices.js';\nexport { InboundProductInvoicesResource, createInboundProductInvoicesResource } from './inbound-product-invoices.js';\nexport { ProductInvoiceQueryResource, createProductInvoiceQueryResource, NFE_QUERY_API_BASE_URL } from './product-invoice-query.js';\nexport { ConsumerInvoiceQueryResource, createConsumerInvoiceQueryResource } from './consumer-invoice-query.js';\nexport { LegalEntityLookupResource, createLegalEntityLookupResource, LEGAL_ENTITY_API_BASE_URL } from './legal-entity-lookup.js';\nexport { NaturalPersonLookupResource, createNaturalPersonLookupResource, NATURAL_PERSON_API_BASE_URL } from './natural-person-lookup.js';\nexport { TaxCalculationResource, createTaxCalculationResource } from './tax-calculation.js';\nexport { TaxCodesResource, createTaxCodesResource } from './tax-codes.js';\nexport { ProductInvoicesResource } from './product-invoices.js';\nexport { StateTaxesResource } from './state-taxes.js';\nexport { ServiceInvoicesRtcResource, createServiceInvoicesRtcResource } from './service-invoices-rtc.js';\nexport { ProductInvoicesRtcResource, createProductInvoicesRtcResource } from './product-invoices-rtc.js';\nexport { MunicipalTaxesResource, createMunicipalTaxesResource } from './municipal-taxes.js';\nexport { ConsumerInvoicesResource, createConsumerInvoicesResource } from './consumer-invoices.js';\nexport type { ConsumerInvoicePageOptions } from './consumer-invoices.js';\nexport { CertificatesResource, createCertificatesResource } from './certificates.js';\nexport { NotificationsResource, createNotificationsResource } from './notifications.js';\n","/**\n * @fileoverview NFE.io SDK v3 - Main Client\n *\n * @description\n * Core client class for interacting with the NFE.io API v1.\n * Provides a modern TypeScript interface with zero runtime dependencies.\n *\n * @module nfe-io/client\n * @author NFE.io\n * @license MIT\n */\n\nimport type {\n  NfeConfig,\n  RequiredNfeConfig,\n  ServiceInvoice,\n  PollOptions\n} from './types.js';\nimport { HttpClient, createDefaultRetryConfig, buildHttpConfig } from './http/client.js';\nimport { ErrorFactory, ConfigurationError, PollingTimeoutError } from './errors/index.js';\n\n// Resource imports\nimport {\n  ServiceInvoicesResource,\n  CompaniesResource,\n  LegalPeopleResource,\n  NaturalPeopleResource,\n  WebhooksResource,\n  AddressesResource,\n  TransportationInvoicesResource,\n  InboundProductInvoicesResource,\n  ProductInvoiceQueryResource,\n  ConsumerInvoiceQueryResource,\n  LegalEntityLookupResource,\n  NaturalPersonLookupResource,\n  TaxCalculationResource,\n  TaxCodesResource,\n  ProductInvoicesResource,\n  StateTaxesResource,\n  ServiceInvoicesRtcResource,\n  ProductInvoicesRtcResource,\n  MunicipalTaxesResource,\n  ConsumerInvoicesResource,\n  CertificatesResource,\n  NotificationsResource,\n  ADDRESS_API_BASE_URL,\n  NFE_QUERY_API_BASE_URL,\n  LEGAL_ENTITY_API_BASE_URL,\n  NATURAL_PERSON_API_BASE_URL\n} from './resources/index.js';\nimport { VERSION as PKG_VERSION } from '../version.js';\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Base URL for CT-e API (Transportation Invoices) */\nexport const CTE_API_BASE_URL = 'https://api.nfse.io';\n\n/** Base URL for Legal Entity API (CNPJ Lookup) */\nexport { LEGAL_ENTITY_API_BASE_URL } from './resources/index.js';\n\n/** Base URL for Natural Person API (CPF Lookup) */\nexport { NATURAL_PERSON_API_BASE_URL } from './resources/index.js';\n\n// ============================================================================\n// Main NFE.io Client\n// ============================================================================\n\n/**\n * Main NFE.io API Client\n *\n * @description\n * Primary client class for interacting with the NFE.io API. Provides access to all\n * API resources including service invoices, companies, legal/natural people, and webhooks.\n *\n * **Features:**\n * - Zero runtime dependencies (uses native fetch)\n * - Automatic retry with exponential backoff\n * - TypeScript type safety\n * - Async invoice processing with polling utilities\n * - Environment detection and validation\n *\n * @example Basic Usage\n * ```typescript\n * import { NfeClient } from 'nfe-io';\n *\n * const nfe = new NfeClient({\n *   apiKey: 'your-api-key',\n *   environment: 'production' // or 'sandbox'\n * });\n *\n * // Create a company\n * const company = await nfe.companies.create({\n *   federalTaxNumber: '12345678000190',\n *   name: 'My Company'\n * });\n *\n * // Issue a service invoice\n * const invoice = await nfe.serviceInvoices.create(company.id, {\n *   borrower: { /* ... *\\/ },\n *   cityServiceCode: '12345',\n *   servicesAmount: 1000.00\n * });\n * ```\n *\n * @example With Custom Configuration\n * ```typescript\n * const nfe = new NfeClient({\n *   apiKey: process.env.NFE_API_KEY,\n *   environment: 'production',\n *   timeout: 60000, // 60 seconds\n *   retryConfig: {\n *     maxRetries: 5,\n *     baseDelay: 1000,\n *     maxDelay: 30000\n *   }\n * });\n * ```\n *\n * @example Async Invoice Processing\n * ```typescript\n * // Method 1: Manual polling\n * const result = await nfe.serviceInvoices.create(companyId, data);\n * if (result.status === 'pending') {\n *   const invoice = await nfe.pollUntilComplete(\n *     () => nfe.serviceInvoices.retrieve(companyId, result.id)\n *   );\n * }\n *\n * // Method 2: Automatic polling (recommended)\n * const invoice = await nfe.serviceInvoices.createAndWait(companyId, data, {\n *   maxAttempts: 30,\n *   interval: 2000 // Check every 2 seconds\n * });\n * ```\n *\n * @see {@link NfeConfig} for configuration options\n * @see {@link ServiceInvoicesResource} for invoice operations\n * @see {@link CompaniesResource} for company operations\n */\nexport class NfeClient {\n  /** @internal HTTP client for main API requests (created lazily) */\n  private _http: HttpClient | undefined;\n\n  /** @internal HTTP client for address API requests (created lazily) */\n  private _addressHttp: HttpClient | undefined;\n\n  /** @internal HTTP client for CT-e API requests (created lazily) */\n  private _nfseHttp: HttpClient | undefined;\n  private _webhooksAccountHttp: HttpClient | undefined;\n\n  /** @internal HTTP client for NF-e query API requests (created lazily) */\n  private _nfeQueryHttp: HttpClient | undefined;\n\n  /** @internal HTTP client for Legal Entity API requests (created lazily) */\n  private _legalEntityHttp: HttpClient | undefined;\n\n  /** @internal HTTP client for Natural Person API requests (created lazily) */\n  private _naturalPersonHttp: HttpClient | undefined;\n\n  /** @internal Normalized client configuration */\n  private readonly config: RequiredNfeConfig;\n\n  /** @internal Cached resource instances */\n  private _serviceInvoices: ServiceInvoicesResource | undefined;\n  private _companies: CompaniesResource | undefined;\n  private _legalPeople: LegalPeopleResource | undefined;\n  private _naturalPeople: NaturalPeopleResource | undefined;\n  private _webhooks: WebhooksResource | undefined;\n  private _addresses: AddressesResource | undefined;\n  private _transportationInvoices: TransportationInvoicesResource | undefined;\n  private _inboundProductInvoices: InboundProductInvoicesResource | undefined;\n  private _productInvoiceQuery: ProductInvoiceQueryResource | undefined;\n  private _consumerInvoiceQuery: ConsumerInvoiceQueryResource | undefined;\n  private _legalEntityLookup: LegalEntityLookupResource | undefined;\n  private _naturalPersonLookup: NaturalPersonLookupResource | undefined;\n  private _taxCalculation: TaxCalculationResource | undefined;\n  private _taxCodes: TaxCodesResource | undefined;\n  private _productInvoices: ProductInvoicesResource | undefined;\n  private _stateTaxes: StateTaxesResource | undefined;\n  private _serviceInvoicesRtc: ServiceInvoicesRtcResource | undefined;\n  private _productInvoicesRtc: ProductInvoicesRtcResource | undefined;\n  private _municipalTaxes: MunicipalTaxesResource | undefined;\n  private _consumerInvoices: ConsumerInvoicesResource | undefined;\n  private _certificates: CertificatesResource | undefined;\n  private _notifications: NotificationsResource | undefined;\n\n  /**\n   * Service Invoices API resource\n   *\n   * @description\n   * Provides operations for managing service invoices (NFS-e):\n   * - Create, list, retrieve, cancel service invoices\n   * - Send invoices by email\n   * - Download PDF and XML files\n   * - Automatic polling for async invoice processing\n   *\n   * @see {@link ServiceInvoicesResource}\n   * @throws {ConfigurationError} If API key is not configured\n   *\n   * @example\n   * ```typescript\n   * const invoice = await nfe.serviceInvoices.create(companyId, {\n   *   borrower: { name: 'Client', email: 'client@example.com' },\n   *   cityServiceCode: '12345',\n   *   servicesAmount: 1000.00\n   * });\n   * ```\n   */\n  get serviceInvoices(): ServiceInvoicesResource {\n    if (!this._serviceInvoices) {\n      this._serviceInvoices = new ServiceInvoicesResource(this.getMainHttpClient());\n    }\n    return this._serviceInvoices;\n  }\n\n  /**\n   * Companies API resource\n   *\n   * @description\n   * Provides operations for managing companies:\n   * - CRUD operations for companies\n   * - Upload digital certificates (PFX/P12)\n   * - Batch operations\n   *\n   * @see {@link CompaniesResource}\n   * @throws {ConfigurationError} If API key is not configured\n   *\n   * @example\n   * ```typescript\n   * const company = await nfe.companies.create({\n   *   federalTaxNumber: '12345678000190',\n   *   name: 'My Company',\n   *   email: 'company@example.com'\n   * });\n   * ```\n   */\n  get companies(): CompaniesResource {\n    if (!this._companies) {\n      this._companies = new CompaniesResource(this.getMainHttpClient(), this.getNfseHttpClient());\n    }\n    return this._companies;\n  }\n\n  /**\n   * Legal People API resource\n   *\n   * @description\n   * Provides operations for managing legal persons (empresas/PJ):\n   * - CRUD operations scoped by company\n   * - CNPJ lookup and validation\n   * - Batch operations\n   *\n   * @see {@link LegalPeopleResource}\n   * @throws {ConfigurationError} If API key is not configured\n   *\n   * @example\n   * ```typescript\n   * const legalPerson = await nfe.legalPeople.create(companyId, {\n   *   federalTaxNumber: '12345678000190',\n   *   name: 'Legal Person Company'\n   * });\n   * ```\n   */\n  get legalPeople(): LegalPeopleResource {\n    if (!this._legalPeople) {\n      this._legalPeople = new LegalPeopleResource(this.getMainHttpClient());\n    }\n    return this._legalPeople;\n  }\n\n  /**\n   * Natural People API resource\n   *\n   * @description\n   * Provides operations for managing natural persons (pessoas físicas/PF):\n   * - CRUD operations scoped by company\n   * - CPF lookup and validation\n   * - Batch operations\n   *\n   * @see {@link NaturalPeopleResource}\n   * @throws {ConfigurationError} If API key is not configured\n   *\n   * @example\n   * ```typescript\n   * const naturalPerson = await nfe.naturalPeople.create(companyId, {\n   *   federalTaxNumber: '12345678901',\n   *   name: 'John Doe'\n   * });\n   * ```\n   */\n  get naturalPeople(): NaturalPeopleResource {\n    if (!this._naturalPeople) {\n      this._naturalPeople = new NaturalPeopleResource(this.getMainHttpClient());\n    }\n    return this._naturalPeople;\n  }\n\n  /**\n   * Webhooks API resource\n   *\n   * @description\n   * Provides operations for managing webhooks (account-scoped, `/v2/webhooks`):\n   * - CRUD operations for webhook configurations (`*AccountWebhook*` methods)\n   * - Webhook signature validation\n   * - Ping/test webhook delivery\n   * - Fetch available event types from the live API\n   *\n   * The company-scoped methods (`create`, `list`, ...) are deprecated — the\n   * `/v1/companies/{id}/webhooks` route returns 404 on the current API.\n   *\n   * @see {@link WebhooksResource}\n   * @throws {ConfigurationError} If API key is not configured\n   *\n   * @example\n   * ```typescript\n   * const webhook = await nfe.webhooks.createAccountWebhook({\n   *   uri: 'https://example.com/webhook', // precisa responder 2xx já na criação\n   *   contentType: 'json',\n   *   secret: 'um-segredo-de-32-a-64-caracteres-aqui',\n   *   filters: ['service_invoice.issued_successfully', 'service_invoice.cancelled_successfully'],\n   * });\n   * ```\n   */\n  get webhooks(): WebhooksResource {\n    if (!this._webhooks) {\n      this._webhooks = new WebhooksResource(\n        this.getMainHttpClient(),\n        this.getWebhooksAccountHttpClient()\n      );\n    }\n    return this._webhooks;\n  }\n\n  /**\n   * Addresses API resource\n   *\n   * @description\n   * Provides postal code (CEP) lookup for Brazilian addresses. The live API host\n   * supports postal-code lookup only and returns a single {@link Address}.\n   *\n   * **Note:** This resource uses a different API host (address.api.nfe.io).\n   * Configure `dataApiKey` for a separate key, or it will fallback to `apiKey`.\n   *\n   * @see {@link AddressesResource}\n   * @throws {ConfigurationError} If no API key is configured (dataApiKey or apiKey)\n   *\n   * @example\n   * ```typescript\n   * const address = await nfe.addresses.lookupByPostalCode('01310-100');\n   * console.log(address.street); // 'Paulista'\n   * ```\n   */\n  get addresses(): AddressesResource {\n    if (!this._addresses) {\n      this._addresses = new AddressesResource(this.getAddressHttpClient());\n    }\n    return this._addresses;\n  }\n\n  /**\n   * Transportation Invoices (CT-e) API resource\n   *\n   * @description\n   * Provides operations for managing CT-e (Conhecimento de Transporte Eletrônico)\n   * documents via SEFAZ Distribuição DFe:\n   * - Enable/disable automatic CT-e search\n   * - Retrieve CT-e metadata and XML\n   * - Retrieve CT-e event metadata and XML\n   *\n   * **Prerequisites:**\n   * - Company must have a valid A1 digital certificate\n   * - Webhook must be configured to receive CT-e notifications\n   *\n   * **Note:** This resource uses a different API host (api.nfse.io).\n   * Uses the main `apiKey` — `api.nfse.io` is a FISCAL host and rejects the data key with 403.\n   *\n   * @see {@link TransportationInvoicesResource}\n   * @throws {ConfigurationError} If no main API key is configured (apiKey)\n   *\n   * @example\n   * ```typescript\n   * // Enable automatic CT-e search\n   * await nfe.transportationInvoices.enable('company-id');\n   *\n   * // Retrieve CT-e metadata\n   * const cte = await nfe.transportationInvoices.retrieve(\n   *   'company-id',\n   *   '35240112345678000190570010000001231234567890'\n   * );\n   * ```\n   */\n  get transportationInvoices(): TransportationInvoicesResource {\n    if (!this._transportationInvoices) {\n      this._transportationInvoices = new TransportationInvoicesResource(this.getNfseHttpClient());\n    }\n    return this._transportationInvoices;\n  }\n\n  /**\n   * Inbound Product Invoices (NF-e Distribution) API resource\n   *\n   * @description\n   * Provides operations for querying NF-e documents received by a company\n   * via SEFAZ Distribuição DFe:\n   * - Enable/disable automatic NF-e distribution fetch\n   * - Retrieve inbound NF-e metadata by access key\n   * - Download NF-e documents in XML, PDF, and JSON formats\n   * - Send recipient manifest (Manifestação do Destinatário)\n   * - Reprocess webhooks\n   *\n   * **Prerequisites:**\n   * - Company must have a valid A1 digital certificate\n   * - Webhook must be configured to receive NF-e notifications\n   *\n   * **Note:** This resource uses a different API host (api.nfse.io).\n   * Uses the main `apiKey` — `api.nfse.io` is a FISCAL host and rejects the data key with 403.\n   *\n   * @see {@link InboundProductInvoicesResource}\n   * @throws {ConfigurationError} If no main API key is configured (apiKey)\n   *\n   * @example\n   * ```typescript\n   * // Enable automatic NF-e fetch\n   * await nfe.inboundProductInvoices.enableAutoFetch('company-id', {\n   *   startFromNsu: '999999',\n   *   environmentSEFAZ: 'Production',\n   *   webhookVersion: '2'\n   * });\n   *\n   * // Get NF-e details\n   * const doc = await nfe.inboundProductInvoices.getProductInvoiceDetails(\n   *   'company-id',\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * ```\n   */\n  get inboundProductInvoices(): InboundProductInvoicesResource {\n    if (!this._inboundProductInvoices) {\n      this._inboundProductInvoices = new InboundProductInvoicesResource(this.getNfseHttpClient());\n    }\n    return this._inboundProductInvoices;\n  }\n\n  /**\n   * Product Invoice Query (NF-e) API resource\n   *\n   * @description\n   * Provides read-only operations for querying product invoices (NF-e) directly\n   * on SEFAZ by access key — no company scope required:\n   * - Retrieve full invoice details (issuer, buyer, items, totals, transport, payment)\n   * - Download DANFE PDF\n   * - Download raw NF-e XML\n   * - List fiscal events (cancellations, corrections, manifestations)\n   *\n   * **Note:** This resource uses a different API host (nfe.api.nfe.io).\n   * Configure `dataApiKey` for a separate key, or it will fallback to `apiKey`.\n   *\n   * @see {@link ProductInvoiceQueryResource}\n   * @throws {ConfigurationError} If no API key is configured (dataApiKey or apiKey)\n   *\n   * @example\n   * ```typescript\n   * // Retrieve invoice details\n   * const invoice = await nfe.productInvoiceQuery.retrieve(\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * console.log(invoice.currentStatus); // 'authorized'\n   * console.log(invoice.issuer?.name);\n   *\n   * // Download PDF\n   * const pdf = await nfe.productInvoiceQuery.downloadPdf(\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * fs.writeFileSync('danfe.pdf', pdf);\n   *\n   * // List fiscal events\n   * const events = await nfe.productInvoiceQuery.listEvents(\n   *   '35240112345678000190550010000001231234567890'\n   * );\n   * ```\n   */\n  get productInvoiceQuery(): ProductInvoiceQueryResource {\n    if (!this._productInvoiceQuery) {\n      this._productInvoiceQuery = new ProductInvoiceQueryResource(this.getNfeQueryHttpClient());\n    }\n    return this._productInvoiceQuery;\n  }\n\n  /**\n   * Consumer Invoice Query API resource (CFe-SAT)\n   *\n   * @description\n   * Provides read-only operations for querying CFe-SAT (Cupom Fiscal Eletrônico)\n   * consumer invoices by access key. No company scope required.\n   *\n   * - Retrieve full coupon details (issuer, buyer, items, totals, payment)\n   * - Download original CFe XML\n   *\n   * Uses data API key authentication on `nfe.api.nfe.io`.\n   *\n   * @see {@link ConsumerInvoiceQueryResource}\n   * @throws {ConfigurationError} If API key is not configured\n   *\n   * @example\n   * ```typescript\n   * // Retrieve coupon details\n   * const coupon = await nfe.consumerInvoiceQuery.retrieve(\n   *   '35240112345678000190590000000012341234567890'\n   * );\n   * console.log(coupon.currentStatus); // 'Authorized'\n   * console.log(coupon.issuer?.name);\n   *\n   * // Download CFe XML\n   * const xml = await nfe.consumerInvoiceQuery.downloadXml(\n   *   '35240112345678000190590000000012341234567890'\n   * );\n   * fs.writeFileSync('cfe.xml', xml);\n   * ```\n   */\n  get consumerInvoiceQuery(): ConsumerInvoiceQueryResource {\n    if (!this._consumerInvoiceQuery) {\n      this._consumerInvoiceQuery = new ConsumerInvoiceQueryResource(this.getNfeQueryHttpClient());\n    }\n    return this._consumerInvoiceQuery;\n  }\n\n  /**\n   * Legal Entity Lookup API resource (CNPJ)\n   *\n   * @description\n   * Provides read-only operations for querying Brazilian company (CNPJ) data:\n   * - Basic company info (Receita Federal registry data)\n   * - State tax registration (Inscrição Estadual) lookup\n   * - State tax evaluation for invoice issuance\n   * - Suggested optimal IE for invoice issuance\n   *\n   * **Note:** This resource uses a different API host (legalentity.api.nfe.io).\n   * Configure `dataApiKey` for a separate key, or it will fallback to `apiKey`.\n   *\n   * @see {@link LegalEntityLookupResource}\n   * @throws {ConfigurationError} If no API key is configured (dataApiKey or apiKey)\n   *\n   * @example\n   * ```typescript\n   * // Basic CNPJ lookup\n   * const result = await nfe.legalEntityLookup.getBasicInfo('12.345.678/0001-90');\n   * console.log(result.legalEntity?.name);\n   *\n   * // State tax registration\n   * const stateTax = await nfe.legalEntityLookup.getStateTaxInfo('SP', '12345678000190');\n   * ```\n   */\n  get legalEntityLookup(): LegalEntityLookupResource {\n    if (!this._legalEntityLookup) {\n      this._legalEntityLookup = new LegalEntityLookupResource(this.getLegalEntityHttpClient());\n    }\n    return this._legalEntityLookup;\n  }\n\n  /**\n   * Natural Person Lookup API resource (CPF)\n   *\n   * @description\n   * Provides a read-only operation for querying CPF cadastral status (situação cadastral)\n   * at the Brazilian Federal Revenue Service (Receita Federal).\n   *\n   * **Note:** This resource uses a different API host (naturalperson.api.nfe.io).\n   * Configure `dataApiKey` for a separate key, or it will fallback to `apiKey`.\n   *\n   * @see {@link NaturalPersonLookupResource}\n   * @throws {ConfigurationError} If no API key is configured (dataApiKey or apiKey)\n   *\n   * @example\n   * ```typescript\n   * // CPF cadastral status lookup\n   * const result = await nfe.naturalPersonLookup.getStatus('123.456.789-01', '1990-01-15');\n   * console.log(result.name);    // 'JOÃO DA SILVA'\n   * console.log(result.status);  // 'Regular'\n   * ```\n   */\n  get naturalPersonLookup(): NaturalPersonLookupResource {\n    if (!this._naturalPersonLookup) {\n      this._naturalPersonLookup = new NaturalPersonLookupResource(this.getNaturalPersonHttpClient());\n    }\n    return this._naturalPersonLookup;\n  }\n\n  /**\n   * Tax Calculation Engine API resource\n   *\n   * @description\n   * Provides access to the Motor de Cálculo de Tributos (Tax Calculation Engine)\n   * for computing all applicable Brazilian taxes (ICMS, ICMS-ST, PIS, COFINS,\n   * IPI, II) on product operations.\n   *\n   * **Note:** This resource uses a different API host (api.nfse.io).\n   * Uses the main `apiKey` — `api.nfse.io` is a FISCAL host and rejects the data key with 403.\n   *\n   * @see {@link TaxCalculationResource}\n   * @throws {ConfigurationError} If no main API key is configured (apiKey)\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.taxCalculation.calculate('tenant-id', {\n   *   operationType: 'Outgoing',\n   *   issuer: { state: 'SP', taxRegime: 'RealProfit' },\n   *   recipient: { state: 'RJ' },\n   *   items: [{\n   *     id: '1', operationCode: 121, origin: 'National',\n   *     quantity: 10, unitAmount: 100.00, ncm: '61091000'\n   *   }]\n   * });\n   * ```\n   */\n  get taxCalculation(): TaxCalculationResource {\n    if (!this._taxCalculation) {\n      this._taxCalculation = new TaxCalculationResource(this.getNfseHttpClient());\n    }\n    return this._taxCalculation;\n  }\n\n  /**\n   * Tax Codes API resource (auxiliary reference tables)\n   *\n   * @description\n   * Provides paginated listings of auxiliary tax code reference tables\n   * needed as inputs for the Tax Calculation Engine: operation codes,\n   * acquisition purposes, issuer tax profiles, and recipient tax profiles.\n   *\n   * **Note:** This resource uses a different API host (api.nfse.io).\n   * Uses the main `apiKey` — `api.nfse.io` is a FISCAL host and rejects the data key with 403.\n   *\n   * @see {@link TaxCodesResource}\n   * @see {@link TaxCalculationResource}\n   * @throws {ConfigurationError} If no main API key is configured (apiKey)\n   *\n   * @example\n   * ```typescript\n   * const codes = await nfe.taxCodes.listOperationCodes({ pageIndex: 1, pageCount: 20 });\n   * for (const code of codes.items ?? []) {\n   *   console.log(`${code.code} - ${code.description}`);\n   * }\n   * ```\n   */\n  get taxCodes(): TaxCodesResource {\n    if (!this._taxCodes) {\n      this._taxCodes = new TaxCodesResource(this.getNfseHttpClient());\n    }\n    return this._taxCodes;\n  }\n\n  /**\n   * Product Invoices (NF-e) API resource\n   *\n   * @description\n   * Provides full lifecycle management for NF-e (Nota Fiscal Eletrônica de Produto)\n   * product invoices — issue, list, retrieve, cancel, send correction letters (CC-e),\n   * disable invoice numbers, and download files (PDF/XML).\n   *\n   * **Note:** This resource uses the api.nfse.io host.\n   * Uses the main `apiKey` — `api.nfse.io` is a FISCAL host and rejects the data key with 403.\n   *\n   * @see {@link ProductInvoicesResource}\n   * @throws {ConfigurationError} If no main API key is configured (apiKey)\n   *\n   * @example\n   * ```typescript\n   * const result = await nfe.productInvoices.create('company-id', invoiceData);\n   * const invoices = await nfe.productInvoices.list('company-id', { environment: 'Production' });\n   * ```\n   */\n  get productInvoices(): ProductInvoicesResource {\n    if (!this._productInvoices) {\n      this._productInvoices = new ProductInvoicesResource(this.getNfseHttpClient());\n    }\n    return this._productInvoices;\n  }\n\n  /**\n   * State Taxes (Inscrições Estaduais) API resource\n   *\n   * @description\n   * Provides CRUD operations for company state tax registrations required for\n   * NF-e product invoice issuance — list, create, retrieve, update, and delete.\n   *\n   * **Note:** This resource uses the api.nfse.io host.\n   * Uses the main `apiKey` — `api.nfse.io` is a FISCAL host and rejects the data key with 403.\n   *\n   * @see {@link StateTaxesResource}\n   * @throws {ConfigurationError} If no main API key is configured (apiKey)\n   *\n   * @example\n   * ```typescript\n   * const taxes = await nfe.stateTaxes.list('company-id');\n   * const tax = await nfe.stateTaxes.create('company-id', { taxNumber: '123', serie: 1, number: 1 });\n   * ```\n   */\n  get stateTaxes(): StateTaxesResource {\n    if (!this._stateTaxes) {\n      this._stateTaxes = new StateTaxesResource(this.getNfseHttpClient());\n    }\n    return this._stateTaxes;\n  }\n\n  /**\n   * Service Invoices RTC resource — emit NFS-e under the Reforma Tributária layout\n   * (IBS/CBS groups). Uses the main host (api.nfe.io); supports polling. Emission\n   * is opt-in via this resource; retrieve/cancel/PDF/XML are shared with\n   * {@link serviceInvoices}.\n   */\n  get serviceInvoicesRtc(): ServiceInvoicesRtcResource {\n    if (!this._serviceInvoicesRtc) {\n      this._serviceInvoicesRtc = new ServiceInvoicesRtcResource(this.getMainHttpClient());\n    }\n    return this._serviceInvoicesRtc;\n  }\n\n  /**\n   * Product Invoices RTC resource — emit NF-e/NFC-e under the Reforma Tributária\n   * layout (IBS state+municipal, CBS, IS). Uses api.nfse.io; webhook-driven (not\n   * polled), mirroring {@link productInvoices}.\n   */\n  get productInvoicesRtc(): ProductInvoicesRtcResource {\n    if (!this._productInvoicesRtc) {\n      this._productInvoicesRtc = new ProductInvoicesRtcResource(this.getNfseHttpClient());\n    }\n    return this._productInvoicesRtc;\n  }\n\n  /**\n   * Municipal Taxes resource — CRUD for company municipal tax registrations\n   * (Inscrições Municipais), prerequisite for NFS-e issuance. Uses api.nfse.io.\n   */\n  get municipalTaxes(): MunicipalTaxesResource {\n    if (!this._municipalTaxes) {\n      this._municipalTaxes = new MunicipalTaxesResource(this.getNfseHttpClient());\n    }\n    return this._municipalTaxes;\n  }\n\n  /**\n   * Consumer Invoices resource — emit & manage NFC-e (company-scoped) on\n   * api.nfse.io. Webhook-driven emission. Distinct from {@link consumerInvoiceQuery}\n   * (read-only coupon lookup).\n   */\n  get consumerInvoices(): ConsumerInvoicesResource {\n    if (!this._consumerInvoices) {\n      this._consumerInvoices = new ConsumerInvoicesResource(this.getNfseHttpClient());\n    }\n    return this._consumerInvoices;\n  }\n\n  /**\n   * Certificates resource — manage company digital certificates (retrieve/delete\n   * by thumbprint, list) via the contribuintes-v2 API on api.nfse.io. Complements\n   * the legacy `companies.uploadCertificate` (which targets the api.nfe.io host).\n   */\n  get certificates(): CertificatesResource {\n    if (!this._certificates) {\n      this._certificates = new CertificatesResource(this.getNfseHttpClient());\n    }\n    return this._certificates;\n  }\n\n  /**\n   * Notifications resource — company notification operations (api.nfe.io).\n   */\n  get notifications(): NotificationsResource {\n    if (!this._notifications) {\n      this._notifications = new NotificationsResource(this.getMainHttpClient());\n    }\n    return this._notifications;\n  }\n\n  /**\n   * Create a new NFE.io API client\n   *\n   * @param config - Client configuration options\n   * @throws {ConfigurationError} If configuration is invalid\n   * @throws {ConfigurationError} If Node.js version < 18\n   * @throws {ConfigurationError} If fetch API is not available\n   *\n   * @example Basic\n   * ```typescript\n   * const nfe = new NfeClient({\n   *   apiKey: 'your-api-key',\n   *   environment: 'production'\n   * });\n   * ```\n   *\n   * @example With environment variable\n   * ```typescript\n   * // Set NFE_API_KEY environment variable\n   * const nfe = new NfeClient({\n   *   environment: 'production'\n   * });\n   * ```\n   *\n   * @example With custom retry config\n   * ```typescript\n   * const nfe = new NfeClient({\n   *   apiKey: 'your-api-key',\n   *   timeout: 60000,\n   *   retryConfig: {\n   *     maxRetries: 5,\n   *     baseDelay: 1000,\n   *     maxDelay: 30000\n   *   }\n   * });\n   * ```\n   *\n   * @example With only data API key\n   * ```typescript\n   * // Only use data services (address lookup, CT-e), no main API access\n   * const nfe = new NfeClient({\n   *   dataApiKey: 'data-api-key'\n   * });\n   * await nfe.addresses.lookupByPostalCode('01310-100');\n   * ```\n   */\n  constructor(config: NfeConfig = {}) {\n    // Validate Node.js environment first\n    this.validateEnvironment();\n\n    // Validate and normalize configuration (no longer requires apiKey)\n    this.config = this.validateAndNormalizeConfig(config);\n\n    // Resources are initialized lazily via getters\n  }\n\n  // --------------------------------------------------------------------------\n  // HTTP Client Management (Lazy Initialization)\n  // --------------------------------------------------------------------------\n\n  /**\n   * Get or create the main API HTTP client\n   * @throws {ConfigurationError} If no API key is configured\n   */\n  private getMainHttpClient(): HttpClient {\n    if (!this._http) {\n      const apiKey = this.resolveMainApiKey();\n      if (!apiKey) {\n        throw new ConfigurationError(\n          'API key required for this resource. Set \"apiKey\" in config or NFE_API_KEY environment variable.'\n        );\n      }\n      const httpConfig = buildHttpConfig(\n        apiKey,\n        this.config.baseUrl,\n        this.config.timeout,\n        this.config.retryConfig\n      );\n      this._http = new HttpClient(httpConfig);\n    }\n    return this._http;\n  }\n\n  /**\n   * Get or create the Address API HTTP client\n   * @throws {ConfigurationError} If no API key is configured\n   */\n  private getAddressHttpClient(): HttpClient {\n    if (!this._addressHttp) {\n      const apiKey = this.resolveDataApiKey();\n      if (!apiKey) {\n        throw new ConfigurationError(\n          'API key required for data services. Set \"dataApiKey\" or \"apiKey\" in config, or NFE_DATA_API_KEY/NFE_API_KEY environment variable.'\n        );\n      }\n      const httpConfig = buildHttpConfig(\n        apiKey,\n        ADDRESS_API_BASE_URL,\n        this.config.timeout,\n        this.config.retryConfig\n      );\n      this._addressHttp = new HttpClient(httpConfig);\n    }\n    return this._addressHttp;\n  }\n\n  /**\n   * Resolve the main API key using fallback chain\n   */\n  private resolveMainApiKey(): string | undefined {\n    return (\n      this.config.apiKey ||\n      this.getEnvironmentVariable('NFE_API_KEY')\n    );\n  }\n\n  /**\n   * Resolve the data API key using fallback chain\n   * Order: dataApiKey → apiKey → NFE_DATA_API_KEY → NFE_API_KEY\n   */\n  private resolveDataApiKey(): string | undefined {\n    return (\n      this.config.dataApiKey ||\n      this.config.apiKey ||\n      this.getEnvironmentVariable('NFE_DATA_API_KEY') ||\n      this.getEnvironmentVariable('NFE_API_KEY')\n    );\n  }\n\n  /**\n   * Get or create the HTTP client for `api.nfse.io` — the FISCAL host.\n   *\n   * Every resource on this host uses the MAIN api key. The two platform keys are\n   * complementary, not interchangeable: the data key is rejected with 403 here,\n   * and the main key is rejected with 403 on the lookup hosts\n   * (`nfe.api.nfe.io`, `legalentity`, `naturalperson`, `address`).\n   * Verified live on 2026-09-01 — see tests/fixtures/live-contracts/api-key-host-matrix.json.\n   *\n   * @throws {ConfigurationError} If no main API key is configured\n   */\n  private getNfseHttpClient(): HttpClient {\n    if (!this._nfseHttp) {\n      const apiKey = this.resolveMainApiKey();\n      if (!apiKey) {\n        throw new ConfigurationError(\n          'API key required for this resource. Set \"apiKey\" in config or NFE_API_KEY environment variable.'\n        );\n      }\n      const httpConfig = buildHttpConfig(\n        apiKey,\n        CTE_API_BASE_URL,\n        this.config.timeout,\n        this.config.retryConfig\n      );\n      this._nfseHttp = new HttpClient(httpConfig);\n    }\n    return this._nfseHttp;\n  }\n\n  /**\n   * Get or create the HTTP client for ACCOUNT-scoped webhook endpoints. These\n   * live at the host root under `/v2` (e.g. https://api.nfe.io/v2/webhooks) and\n   * use the MAIN key — NOT under the `/v1` base of the main client.\n   * @throws {ConfigurationError} If no main API key is configured\n   */\n  private getWebhooksAccountHttpClient(): HttpClient {\n    if (!this._webhooksAccountHttp) {\n      const apiKey = this.resolveMainApiKey();\n      if (!apiKey) {\n        throw new ConfigurationError(\n          'API key required for this resource. Set \"apiKey\" in config or NFE_API_KEY environment variable.'\n        );\n      }\n      // Account webhooks are at host-root /v2, not under the /v1 main base.\n      const v2BaseUrl = this.config.baseUrl.replace(/\\/v1(\\/)?$/, '/v2');\n      const httpConfig = buildHttpConfig(\n        apiKey,\n        v2BaseUrl,\n        this.config.timeout,\n        this.config.retryConfig\n      );\n      this._webhooksAccountHttp = new HttpClient(httpConfig);\n    }\n    return this._webhooksAccountHttp;\n  }\n\n  /**\n   * Get or create the NF-e Query API HTTP client (nfe.api.nfe.io)\n   * @throws {ConfigurationError} If no API key is configured\n   */\n  private getNfeQueryHttpClient(): HttpClient {\n    if (!this._nfeQueryHttp) {\n      const apiKey = this.resolveDataApiKey();\n      if (!apiKey) {\n        throw new ConfigurationError(\n          'API key required for data services. Set \"dataApiKey\" or \"apiKey\" in config, or NFE_DATA_API_KEY/NFE_API_KEY environment variable.'\n        );\n      }\n      const httpConfig = buildHttpConfig(\n        apiKey,\n        NFE_QUERY_API_BASE_URL,\n        this.config.timeout,\n        this.config.retryConfig\n      );\n      this._nfeQueryHttp = new HttpClient(httpConfig);\n    }\n    return this._nfeQueryHttp;\n  }\n\n  /**\n   * Get or create the Legal Entity API HTTP client (legalentity.api.nfe.io)\n   * @throws {ConfigurationError} If no API key is configured\n   */\n  private getLegalEntityHttpClient(): HttpClient {\n    if (!this._legalEntityHttp) {\n      const apiKey = this.resolveDataApiKey();\n      if (!apiKey) {\n        throw new ConfigurationError(\n          'API key required for data services. Set \"dataApiKey\" or \"apiKey\" in config, or NFE_DATA_API_KEY/NFE_API_KEY environment variable.'\n        );\n      }\n      const httpConfig = buildHttpConfig(\n        apiKey,\n        LEGAL_ENTITY_API_BASE_URL,\n        this.config.timeout,\n        this.config.retryConfig\n      );\n      this._legalEntityHttp = new HttpClient(httpConfig);\n    }\n    return this._legalEntityHttp;\n  }\n\n  /**\n   * Get or create the Natural Person API HTTP client (naturalperson.api.nfe.io)\n   * @throws {ConfigurationError} If no API key is configured\n   */\n  private getNaturalPersonHttpClient(): HttpClient {\n    if (!this._naturalPersonHttp) {\n      const apiKey = this.resolveDataApiKey();\n      if (!apiKey) {\n        throw new ConfigurationError(\n          'API key required for data services. Set \"dataApiKey\" or \"apiKey\" in config, or NFE_DATA_API_KEY/NFE_API_KEY environment variable.'\n        );\n      }\n      const httpConfig = buildHttpConfig(\n        apiKey,\n        NATURAL_PERSON_API_BASE_URL,\n        this.config.timeout,\n        this.config.retryConfig\n      );\n      this._naturalPersonHttp = new HttpClient(httpConfig);\n    }\n    return this._naturalPersonHttp;\n  }\n\n  // --------------------------------------------------------------------------\n  // Configuration Management\n  // --------------------------------------------------------------------------\n\n  private validateAndNormalizeConfig(config: NfeConfig): RequiredNfeConfig {\n    // API keys are now optional - validated lazily when resources are accessed\n    const apiKey = config.apiKey?.trim() || undefined;\n    const dataApiKey = config.dataApiKey?.trim() || undefined;\n\n    // Normalize environment\n    const environment = config.environment || 'production';\n    if (!['production', 'development'].includes(environment)) {\n      throw new ConfigurationError(\n        `Invalid environment: ${environment}. Must be 'production' or 'development'.`,\n        { environment }\n      );\n    }\n\n    // Set defaults - ensure retryConfig has all required properties\n    const defaultRetryConfig = createDefaultRetryConfig();\n    const retryConfig = config.retryConfig\n      ? { ...defaultRetryConfig, ...config.retryConfig }\n      : defaultRetryConfig;\n\n    const normalizedConfig: RequiredNfeConfig = {\n      apiKey,\n      dataApiKey,\n      environment,\n      baseUrl: config.baseUrl || this.getDefaultBaseUrl(),\n      timeout: config.timeout || 30000,\n      retryConfig,\n    };\n\n    return normalizedConfig;\n  }\n\n  private getDefaultBaseUrl(): string {\n    // NFE.io API uses the same endpoint for both production and development\n    // They are differentiated by the API key used, not by different URLs\n    return 'https://api.nfe.io/v1';\n  }\n\n  private getEnvironmentVariable(name: string): string | undefined {\n    // Safe access to process.env with fallback\n    try {\n      return (globalThis as any).process?.env?.[name];\n    } catch {\n      return undefined;\n    }\n  }\n\n  // --------------------------------------------------------------------------\n  // Environment Validation\n  // --------------------------------------------------------------------------\n\n  private validateEnvironment(): void {\n    // Check Node.js version (should support fetch natively)\n    this.validateNodeVersion();\n\n    // Check fetch availability\n    if (typeof fetch === 'undefined') {\n      throw ErrorFactory.fromNodeVersionError(this.getNodeVersion());\n    }\n  }\n\n  private validateNodeVersion(): void {\n    const nodeVersion = this.getNodeVersion();\n    const majorVersion = this.extractMajorVersion(nodeVersion);\n\n    if (majorVersion < 18) {\n      throw ErrorFactory.fromNodeVersionError(nodeVersion);\n    }\n  }\n\n  private getNodeVersion(): string {\n    try {\n      return (globalThis as any).process?.version || 'unknown';\n    } catch {\n      return 'unknown';\n    }\n  }\n\n  private extractMajorVersion(version: string): number {\n    const match = version.match(/^v?(\\d+)\\./);\n    return match ? parseInt(match[1]!, 10) : 0;\n  }\n\n  // --------------------------------------------------------------------------\n  // Public Utility Methods\n  // --------------------------------------------------------------------------\n\n  /**\n   * Update client configuration dynamically\n   *\n   * @param newConfig - Partial configuration to merge with existing config\n   * @throws {ConfigurationError} If new configuration is invalid\n   *\n   * @example\n   * ```typescript\n   * const nfe = new NfeClient({ apiKey: 'old-key' });\n   *\n   * // Switch to sandbox environment\n   * nfe.updateConfig({ environment: 'sandbox' });\n   *\n   * // Update timeout\n   * nfe.updateConfig({ timeout: 60000 });\n   * ```\n   */\n  public updateConfig(newConfig: Partial<NfeConfig>): void {\n    // Normalize the new configuration with current values as defaults\n    const normalizedConfig = this.validateAndNormalizeConfig({\n      ...newConfig,\n      // Use current values as fallbacks for unspecified fields\n      environment: newConfig.environment ?? this.config.environment,\n      baseUrl: newConfig.baseUrl ?? this.config.baseUrl,\n      timeout: newConfig.timeout ?? this.config.timeout,\n      retryConfig: newConfig.retryConfig ?? this.config.retryConfig,\n    });\n\n    // Override API keys if they were in current config but not in newConfig\n    if (normalizedConfig.apiKey === undefined && this.config.apiKey !== undefined && newConfig.apiKey === undefined) {\n      normalizedConfig.apiKey = this.config.apiKey;\n    }\n    if (normalizedConfig.dataApiKey === undefined && this.config.dataApiKey !== undefined && newConfig.dataApiKey === undefined) {\n      normalizedConfig.dataApiKey = this.config.dataApiKey;\n    }\n\n    // Update internal config\n    Object.assign(this.config, normalizedConfig);\n\n    // Clear ALL cached HTTP clients and resources so they're recreated with new config.\n    this.resetCaches();\n  }\n\n  /**\n   * Invalidate every lazily-cached HTTP client and resource.\n   *\n   * Must list every `_*Http` and resource field so that, after `updateConfig`,\n   * no cached instance retains a stale baseUrl/apiKey/timeout. When adding a new\n   * resource or HTTP client, add it here too (single source of cache truth).\n   */\n  private resetCaches(): void {\n    // HTTP clients\n    this._http = undefined;\n    this._addressHttp = undefined;\n    this._nfseHttp = undefined;\n    this._webhooksAccountHttp = undefined;\n    this._nfeQueryHttp = undefined;\n    this._legalEntityHttp = undefined;\n    this._naturalPersonHttp = undefined;\n    // Resources\n    this._serviceInvoices = undefined;\n    this._companies = undefined;\n    this._legalPeople = undefined;\n    this._naturalPeople = undefined;\n    this._webhooks = undefined;\n    this._addresses = undefined;\n    this._transportationInvoices = undefined;\n    this._inboundProductInvoices = undefined;\n    this._productInvoiceQuery = undefined;\n    this._consumerInvoiceQuery = undefined;\n    this._legalEntityLookup = undefined;\n    this._naturalPersonLookup = undefined;\n    this._taxCalculation = undefined;\n    this._taxCodes = undefined;\n    this._productInvoices = undefined;\n    this._stateTaxes = undefined;\n    this._serviceInvoicesRtc = undefined;\n    this._productInvoicesRtc = undefined;\n    this._municipalTaxes = undefined;\n    this._consumerInvoices = undefined;\n    this._certificates = undefined;\n    this._notifications = undefined;\n  }\n\n  /**\n   * Set request timeout in milliseconds\n   *\n   * @param timeout - Request timeout in milliseconds\n   *\n   * @description\n   * Maintains v2 API compatibility. Equivalent to `updateConfig({ timeout })`.\n   *\n   * @example\n   * ```typescript\n   * nfe.setTimeout(60000); // 60 seconds\n   * ```\n   */\n  public setTimeout(timeout: number): void {\n    this.updateConfig({ timeout });\n  }\n\n  /**\n   * Set or update API key\n   *\n   * @param apiKey - New API key to use for authentication\n   *\n   * @description\n   * Maintains v2 API compatibility. Equivalent to `updateConfig({ apiKey })`.\n   *\n   * @example\n   * ```typescript\n   * nfe.setApiKey('new-api-key');\n   * ```\n   */\n  public setApiKey(apiKey: string): void {\n    this.updateConfig({ apiKey });\n  }\n\n  /**\n   * Get current client configuration\n   *\n   * @returns Readonly copy of current configuration\n   *\n   * @example\n   * ```typescript\n   * const config = nfe.getConfig();\n   * console.log('Environment:', config.environment);\n   * console.log('Base URL:', config.baseUrl);\n   * console.log('Timeout:', config.timeout);\n   * ```\n   */\n  public getConfig(): Readonly<RequiredNfeConfig> {\n    return { ...this.config };\n  }\n\n  // --------------------------------------------------------------------------\n  // Polling Utility (for async invoice processing)\n  // --------------------------------------------------------------------------\n\n  /**\n   * Poll a resource until it completes or times out\n   *\n   * @template T - Type of the resource being polled\n   * @param locationUrl - URL or path to poll\n   * @param options - Polling configuration\n   * @returns Promise that resolves when resource is complete\n   * @throws {PollingTimeoutError} If polling exceeds maxAttempts\n   *\n   * @description\n   * Critical utility for NFE.io's async invoice processing. When creating a service\n   * invoice, the API returns a 202 response with a location URL. This method polls\n   * that URL until the invoice is fully processed or the polling times out.\n   *\n   * @example Basic usage\n   * ```typescript\n   * const result = await nfe.serviceInvoices.create(companyId, data);\n   *\n   * if (result.status === 'pending') {\n   *   const invoice = await nfe.pollUntilComplete(result.location);\n   *   console.log('Invoice issued:', invoice.number);\n   * }\n   * ```\n   *\n   * @example With custom polling options\n   * ```typescript\n   * const invoice = await nfe.pollUntilComplete(locationUrl, {\n   *   maxAttempts: 60,  // Poll up to 60 times\n   *   intervalMs: 3000  // Wait 3 seconds between attempts\n   * });\n   * ```\n   *\n   * @example Using createAndWait (recommended)\n   * ```typescript\n   * // Instead of manual polling, use the convenience method:\n   * const invoice = await nfe.serviceInvoices.createAndWait(companyId, data, {\n   *   maxAttempts: 30,\n   *   interval: 2000\n   * });\n   * ```\n   *\n   * @see {@link PollOptions} for configuration options\n   * @see {@link ServiceInvoicesResource.createAndWait} for automated polling\n   */\n  public async pollUntilComplete<T = ServiceInvoice>(\n    locationUrl: string,\n    options: PollOptions = {}\n  ): Promise<T> {\n    const {\n      maxAttempts = 30,\n      intervalMs = 2000\n    } = options;\n\n    for (let attempt = 0; attempt < maxAttempts; attempt++) {\n      // Wait before polling (except first attempt)\n      if (attempt > 0) {\n        await this.sleep(intervalMs);\n      }\n\n      try {\n        // Extract path from full URL for HTTP client\n        const path = this.extractPathFromUrl(locationUrl);\n        const response = await this.getMainHttpClient().get<any>(path);\n\n        // Check completion status\n        if (this.isCompleteResponse(response.data)) {\n          return response.data as T;\n        }\n\n        if (this.isFailedResponse(response.data)) {\n          throw new PollingTimeoutError(\n            `Resource processing failed: ${response.data.error || 'Unknown error'}`,\n            response.data\n          );\n        }\n\n        // Continue polling if still in progress\n\n      } catch (error) {\n        // If it's the last attempt, throw the error\n        if (attempt === maxAttempts - 1) {\n          throw error;\n        }\n\n        // For other attempts, continue polling (might be temporary network issue)\n      }\n    }\n\n    throw new PollingTimeoutError(\n      `Polling timeout after ${maxAttempts} attempts. Resource may still be processing.`,\n      { maxAttempts, intervalMs }\n    );\n  }\n\n  private extractPathFromUrl(url: string): string {\n    try {\n      const urlObj = new URL(url);\n      return urlObj.pathname + urlObj.search;\n    } catch {\n      // If URL parsing fails, assume it's already a path\n      return url.startsWith('/') ? url : `/${url}`;\n    }\n  }\n\n  private isCompleteResponse(data: any): boolean {\n    return data && (\n      data.status === 'completed' ||\n      data.status === 'issued' ||\n      (data.id && data.number && !data.status) // NFE.io completed invoices might not have explicit status\n    );\n  }\n\n  private isFailedResponse(data: any): boolean {\n    return data && (\n      data.status === 'failed' ||\n      data.status === 'error' ||\n      data.error\n    );\n  }\n\n  private sleep(ms: number): Promise<void> {\n    return new Promise(resolve => setTimeout(resolve, ms));\n  }\n\n  // --------------------------------------------------------------------------\n  // Health Check & Debug\n  // --------------------------------------------------------------------------\n\n  /**\n   * Check if the client is properly configured and can reach the NFE.io API\n   *\n   * @returns Health check result with status and optional error details\n   *\n   * @description\n   * Performs a simple API request to verify connectivity and authentication.\n   * Useful for debugging connection issues or validating client configuration.\n   *\n   * Issues `GET /v1/companies` with no query string — the smallest request the\n   * API accepts on this route. See the implementation note before you add a\n   * pagination parameter here.\n   *\n   * @example\n   * ```typescript\n   * const health = await nfe.healthCheck();\n   *\n   * if (health.status === 'ok') {\n   *   console.log('API connection successful!');\n   * } else {\n   *   console.error('API connection failed:', health.details);\n   * }\n   * ```\n   *\n   * @example In application startup\n   * ```typescript\n   * async function initializeApp() {\n   *   const nfe = new NfeClient({ apiKey: process.env.NFE_API_KEY });\n   *\n   *   const health = await nfe.healthCheck();\n   *   if (health.status !== 'ok') {\n   *     throw new Error(`NFE.io API is not reachable: ${health.details?.error}`);\n   *   }\n   *\n   *   console.log('NFE.io SDK initialized successfully');\n   * }\n   * ```\n   */\n  public async healthCheck(): Promise<{ status: 'ok' | 'error', details?: any }> {\n    try {\n      // Requisicao minima que a API aceita: `GET /v1/companies` sem query.\n      //\n      // NAO reintroduzir `pageCount`. `pageCount=1` responde\n      // 400 \"pageCount must be between 1 and 50\" -- o limite inferior do servidor\n      // esta um a mais do que a propria mensagem diz (medido em 2026-09-02).\n      // Enquanto isso nao for corrigido upstream, qualquer valor aqui seria um\n      // numero magico contornando defeito alheio; a rota sem query responde 200.\n      await this.getMainHttpClient().get('/companies');\n      return { status: 'ok' };\n    } catch (error) {\n      return {\n        status: 'error',\n        details: {\n          error: error instanceof Error ? error.message : 'Unknown error',\n          config: {\n            baseUrl: this.config.baseUrl,\n            environment: this.config.environment,\n            hasApiKey: !!this.config.apiKey,\n          }\n        }\n      };\n    }\n  }\n\n  /**\n   * Get client information for debugging and diagnostics\n   *\n   * @returns Client diagnostic information\n   *\n   * @description\n   * Returns comprehensive information about the current SDK instance,\n   * useful for bug reports and troubleshooting.\n   *\n   * @example\n   * ```typescript\n   * const info = nfe.getClientInfo();\n   * console.log('SDK Version:', info.version);\n   * console.log('Node Version:', info.nodeVersion);\n   * console.log('Environment:', info.environment);\n   * console.log('Base URL:', info.baseUrl);\n   * ```\n   *\n   * @example In error reporting\n   * ```typescript\n   * try {\n   *   await nfe.serviceInvoices.create(companyId, data);\n   * } catch (error) {\n   *   const info = nfe.getClientInfo();\n   *   console.error('Error context:', {\n   *     error: error.message,\n   *     sdkInfo: info\n   *   });\n   * }\n   * ```\n   */\n  public getClientInfo(): {\n    version: string;\n    nodeVersion: string;\n    environment: string;\n    baseUrl: string;\n    hasApiKey: boolean;\n  } {\n    return {\n      version: VERSION,\n      nodeVersion: this.getNodeVersion(),\n      environment: this.config.environment,\n      baseUrl: this.config.baseUrl,\n      hasApiKey: !!this.config.apiKey,\n    };\n  }\n}\n\n// ============================================================================\n// Factory Functions (maintain v2 compatibility)\n// ============================================================================\n\n/**\n * Create NFE.io client instance using factory function\n *\n * @param apiKey - API key string or full configuration object\n * @param _version - API version (ignored in v3, maintained for v2 compatibility)\n * @returns Configured NfeClient instance\n *\n * @description\n * Factory function for creating NFE.io client instances. Maintains v2 API compatibility\n * while providing modern TypeScript support.\n *\n * @example String API key\n * ```typescript\n * const nfe = createNfeClient('your-api-key');\n * ```\n *\n * @example Configuration object\n * ```typescript\n * const nfe = createNfeClient({\n *   apiKey: 'your-api-key',\n *   environment: 'sandbox',\n *   timeout: 60000\n * });\n * ```\n *\n * @example v2 compatibility\n * ```typescript\n * // v2 style (still works)\n * const nfe = createNfeClient('your-api-key');\n * ```\n */\nexport function createNfeClient(apiKey: string | NfeConfig): NfeClient {\n  const config = typeof apiKey === 'string' ? { apiKey } : apiKey;\n  return new NfeClient(config);\n}\n\n/**\n * Default export factory function for CommonJS compatibility\n *\n * @param apiKey - API key string or full configuration object\n * @returns Configured NfeClient instance\n *\n * @description\n * Default export maintains v2 API compatibility for CommonJS users.\n * Equivalent to `createNfeClient()`.\n *\n * @example ES Modules\n * ```typescript\n * import nfe from 'nfe-io';\n * const client = nfe('your-api-key');\n * ```\n *\n * @example CommonJS\n * ```javascript\n * const nfe = require('nfe-io').default;\n * const client = nfe('your-api-key');\n * ```\n */\nexport default function nfe(apiKey: string | NfeConfig): NfeClient {\n  return createNfeClient(apiKey);\n}\n\n// ============================================================================\n// Version Constants\n// ============================================================================\n\n/**\n * Current SDK version\n *\n * Vem de `src/version.ts`, gerado do `package.json` — ver a nota em\n * `PACKAGE_VERSION` (`src/index.ts`) sobre por que não se fixa literal aqui.\n *\n * @constant\n */\nexport const VERSION = PKG_VERSION;\n\n/**\n * Supported Node.js version range (semver format)\n * @constant\n */\nexport const SUPPORTED_NODE_VERSIONS = '>=18.0.0';\n\n/**\n * Default request timeout in milliseconds\n * @constant\n */\nexport const DEFAULT_TIMEOUT = 30000;\n\n/**\n * Default number of retry attempts for failed requests\n * @constant\n */\nexport const DEFAULT_RETRY_ATTEMPTS = 3;\n","/**\n * @fileoverview NFE.io SDK v3 - Official Node.js SDK for NFE.io API\n *\n * @description\n * Modern TypeScript SDK for NFE.io API with zero runtime dependencies.\n * Compatible with Node.js 18+ and modern JavaScript runtimes.\n *\n * @example Basic Usage\n * ```typescript\n * import { NfeClient } from 'nfe-io';\n *\n * const nfe = new NfeClient({\n *   apiKey: 'your-api-key',\n *   environment: 'production' // or 'sandbox'\n * });\n *\n * // Create a service invoice\n * const invoice = await nfe.serviceInvoices.create('company-id', {\n *   borrower: { /* ... *\\/ },\n *   cityServiceCode: '12345',\n *   servicesAmount: 1000.00\n * });\n * ```\n *\n * @example With Polling\n * ```typescript\n * // Automatically poll until invoice is processed\n * const invoice = await nfe.serviceInvoices.createAndWait('company-id', data, {\n *   maxAttempts: 30,\n *   interval: 2000\n * });\n * ```\n *\n * @module nfe-io\n * @version 5.1.0\n * @author NFE.io\n * @license MIT\n */\n\n// ============================================================================\n// Main Exports\n// ============================================================================\n\n/**\n * Core client exports\n *\n * @see {@link NfeClient} - Main client class for NFE.io API\n * @see {@link createNfeClient} - Factory function for creating client instances\n */\nexport { NfeClient, createNfeClient, VERSION, SUPPORTED_NODE_VERSIONS, CTE_API_BASE_URL, LEGAL_ENTITY_API_BASE_URL, NATURAL_PERSON_API_BASE_URL } from './core/client.js';\n\n/**\n * TypeScript type definitions for NFE.io API entities and configurations\n *\n * @see {@link NfeConfig} - Client configuration options\n * @see {@link Company} - Company entity type\n * @see {@link ServiceInvoice} - Service invoice entity type\n * @see {@link LegalPerson} - Legal person (empresa) entity type\n * @see {@link NaturalPerson} - Natural person (pessoa física) entity type\n * @see {@link AccountWebhook} - Webhook configuration type (account-scoped, `/v2/webhooks`)\n */\nexport type {\n  // Configuration\n  NfeConfig,\n  RequiredNfeConfig,\n  RetryConfig,\n\n  // Entities\n  Company,\n  LegalPerson,\n  NaturalPerson,\n  ServiceInvoice,\n  ServiceInvoiceData,\n  ServiceInvoiceDetails,\n  Webhook,\n  WebhookEvent,\n  AccountWebhook,\n  WebhookEventType,\n\n  // Address types\n  Address,\n  AddressCity,\n  AddressLookupResponse,\n\n  // CT-e (Transportation Invoice) types\n  TransportationInvoiceInboundSettings,\n  TransportationInvoiceMetadata,\n  EnableTransportationInvoiceOptions,\n  TransportationInvoiceEntityStatus,\n  TransportationInvoiceMetadataType,\n\n  // Inbound NF-e Distribution types\n  InboundInvoiceMetadata,\n  InboundProductInvoiceMetadata,\n  InboundSettings,\n  EnableInboundOptions,\n  ManifestEventType,\n  InboundCompany,\n  InboundIssuer,\n  InboundBuyer,\n  InboundTransportation,\n  InboundLinks,\n  InboundProductInvoice,\n  AutomaticManifesting,\n\n  // Product Invoice Query types (consulta-nf)\n  ProductInvoiceStatus,\n  ProductInvoicePaymentType,\n  ProductInvoiceOperationType,\n  ProductInvoiceDestination,\n  ProductInvoicePrintType,\n  ProductInvoiceIssueType,\n  ProductInvoiceEnvironmentType,\n  ProductInvoicePurposeType,\n  ProductInvoiceConsumerType,\n  ProductInvoicePresenceType,\n  ProductInvoiceProcessType,\n  ProductInvoiceTaxRegimeCode,\n  ProductInvoicePersonType,\n  ProductInvoicePaymentMethod,\n  ProductInvoiceCardFlag,\n  ProductInvoiceIntegrationPaymentType,\n  ProductInvoiceCity,\n  ProductInvoiceAddress,\n  ProductInvoiceIssuer,\n  ProductInvoiceBuyer,\n  ProductInvoiceIcmsTotals,\n  ProductInvoiceIssqnTotals,\n  ProductInvoiceTotals,\n  ProductInvoiceItemIcms,\n  ProductInvoiceItemTax,\n  ProductInvoiceItem,\n  ProductInvoiceTransport,\n  ProductInvoicePayment,\n  ProductInvoiceProtocol,\n  ProductInvoiceAdditionalInfo,\n  ProductInvoiceBilling,\n  ProductInvoiceDetails,\n  ProductInvoiceEvent,\n  ProductInvoiceEventsResponse,\n\n  // Consumer Invoice Query types (CFe-SAT / consulta-nf-consumidor)\n  CouponStatus,\n  CouponPersonType,\n  CouponTaxRegime,\n  CouponPaymentMethod,\n  CouponIssqnTaxIncentive,\n  CouponCity,\n  CouponAddress,\n  CouponIssuer,\n  CouponBuyer,\n  CouponIcmsTotal,\n  CouponIssqnTotal,\n  CouponTotal,\n  CouponTaxBase,\n  CouponIcmsTax,\n  CouponPisTax,\n  CouponCofinsTax,\n  CouponIssqnTax,\n  CouponItemTax,\n  CouponFiscoField,\n  CouponReferencedDocument,\n  CouponItem,\n  CouponPaymentDetail,\n  CouponPayment,\n  CouponDelivery,\n  CouponAdditionalInformation,\n  TaxCoupon,\n\n  // Legal Entity Lookup types (consulta-cnpj)\n  BrazilianState,\n  LegalEntityBasicInfoOptions,\n  LegalEntityBasicInfoResponse,\n  LegalEntityStateTaxResponse,\n  LegalEntityStateTaxForInvoiceResponse,\n  LegalEntitySize,\n  LegalEntityStatus,\n  LegalEntityUnit,\n  LegalEntityTaxRegime,\n  LegalEntityNatureCode,\n  LegalEntityStateTaxStatus,\n  LegalEntityStateTaxForInvoiceStatus,\n  LegalEntityFiscalDocumentStatus,\n  LegalEntityActivityType,\n  LegalEntityPhoneSource,\n  LegalEntityCity,\n  LegalEntityAddress,\n  LegalEntityPhone,\n  LegalEntityEconomicActivity,\n  LegalEntityNature,\n  LegalEntityQualification,\n  LegalEntityPartner,\n  LegalEntityFiscalDocumentInfo,\n  LegalEntityStateTax,\n  LegalEntityStateTaxForInvoice,\n  LegalEntityBasicInfo,\n  LegalEntityStateTaxInfo,\n  LegalEntityStateTaxForInvoiceInfo,\n\n  // Natural Person Lookup types (consulta-cpf)\n  NaturalPersonStatus,\n  NaturalPersonStatusResponse,\n\n  // Tax Calculation types (calculo-impostos)\n  TaxOperationType,\n  TaxOrigin,\n  TaxCalcTaxRegime,\n  TaxIcms,\n  TaxIcmsUfDest,\n  TaxPis,\n  TaxCofins,\n  TaxIpi,\n  TaxIi,\n  CalculateRequestIssuer,\n  CalculateRequestRecipient,\n  CalculateItemRequest,\n  CalculateRequest,\n  CalculateItemResponse,\n  CalculateResponse,\n  TaxCode,\n  TaxCodePaginatedResponse,\n  TaxCodeListOptions,\n\n  // NF-e Product Invoice types (nf-produto-v2)\n  NfeEnvironmentType,\n  NfeInvoiceStatus,\n  NfeStateCode,\n  NfeOperationType,\n  NfePurposeType,\n  NfePaymentMethod,\n  NfeShippingModality,\n  NfeConsumerPresenceType,\n  NfePrintType,\n  NfePersonType,\n  NfeDestination,\n  NfeConsumerType,\n  NfePaymentType,\n  NfeReceiverStateTaxIndicator,\n  NfeFlagCard,\n  NfeIntegrationPaymentType,\n  NfeIntermediationType,\n  NfeTaxRegime,\n  NfeSpecialTaxRegime,\n  NfeStateTaxProcessingAuthorizer,\n  NfeFlowStatus,\n  NfeAddress,\n  NfeCity,\n  NfeProductInvoiceBuyer,\n  NfeCardResource,\n  NfePaymentDetail,\n  NfePaymentResource,\n  NfeBillingResource,\n  NfeBillingInvoice,\n  NfeDuplicateResource,\n  NfeIcmsTaxResource,\n  NfeIpiTaxResource,\n  NfePisTaxResource,\n  NfeCofinsTaxResource,\n  NfeIiTaxResource,\n  NfeIcmsUfDestinationTaxResource,\n  NfeInvoiceItemTax,\n  NfeTaxDeterminationResource,\n  NfeInvoiceItemResource,\n  NfeTransportInformation,\n  NfeTransportGroupResource,\n  NfeVolumeResource,\n  NfeAdditionalInformation,\n  NfeExportResource,\n  NfeIssuerFromRequest,\n  NfeIntermediateResource,\n  NfeDeliveryInformation,\n  NfeWithdrawalInformation,\n  NfeTotals,\n  NfeTotalResource,\n  NfeAuthorizationResource,\n  NfeContingencyDetails,\n  NfeActivityResource,\n  NfeInvoiceEventsBase,\n  NfeProductInvoiceIssueData,\n  NfeIssuerResource,\n  NfeProductInvoice,\n  NfeProductInvoiceWithoutEvents,\n  NfeProductInvoiceListOptions,\n  NfeProductInvoiceListResponse,\n  NfeInvoiceItemsResponse,\n  NfeProductInvoiceEventsResponse,\n  NfeProductInvoiceSubListOptions,\n  NfeFileResource,\n  InboundFileResource,\n  ConsumerInvoiceItemsResponse,\n  ConsumerInvoiceEventsResponse,\n  ConsumerInvoiceCancellationResponse,\n  ConsumerInvoiceFileResource,\n  NfeRequestCancellationResource,\n  NfeDisablementData,\n  NfeDisablementResource,\n\n  // State Tax (Inscrição Estadual) types\n  NfeStateTaxType,\n  NfeStateTaxEnvironmentType,\n  NfeStateTaxStatus,\n  NfeStateTaxStateCode,\n  NfeStateTaxSpecialTaxRegime,\n  NfeStateTax,\n  NfeStateTaxCreateData,\n  NfeStateTaxUpdateData,\n  NfeStateTaxListResponse,\n  NfeStateTaxListOptions,\n  NfeSecurityCredential,\n\n  // Common types\n  EntityType,\n  TaxRegime,\n  SpecialTaxRegime,\n\n  // HTTP and pagination\n  HttpResponse,\n  ListResponse,\n  PageInfo,\n  PaginationOptions,\n  PollOptions,\n\n  // Utility types\n  ResourceId,\n  ApiErrorResponse,\n\n  // RTC (Reforma Tributária do Consumo) emission request types\n  NFSeRtcRequest,\n  ProductInvoiceRtcRequest,\n\n  // Empresas (contribuintes-v2) spec-backed types\n  CompanyResourceItem,\n  CompanyResourceV1,\n  CreateCompanyResourceItem,\n  UpdateCompanyResourceItem,\n  CompanyV2ListOptions,\n  CompanyV2ListResponse,\n  CertificateMetadataResource,\n  CompanyAddress,\n  MunicipalTax,\n  CreateMunicipalTaxData,\n  UpdateMunicipalTaxData,\n  MunicipalTaxListResponse,\n  ConsumerInvoiceData,\n  ConsumerInvoice,\n  ConsumerInvoiceListResponse,\n  ConsumerInvoiceDisablementData,\n  CertificatesMetadataResource,\n  CertificateMetadataResourceItem,\n  CertificateStatus,\n  CompanyCertificateV1,\n} from './core/types.js';\n\n/**\n * Error classes and utilities for comprehensive error handling\n *\n * @see {@link NfeError} - Base error class for all SDK errors\n * @see {@link AuthenticationError} - Thrown when API key is invalid (401)\n * @see {@link ValidationError} - Thrown when request validation fails (400, 422)\n * @see {@link NotFoundError} - Thrown when resource not found (404)\n * @see {@link RateLimitError} - Thrown when rate limit exceeded (429)\n * @see {@link ServerError} - Thrown on server errors (500, 502, 503)\n * @see {@link ConnectionError} - Thrown on network/connection failures\n * @see {@link TimeoutError} - Thrown when request times out\n * @see {@link PollingTimeoutError} - Thrown when invoice polling times out\n */\nexport {\n  // Base error\n  NfeError,\n\n  // HTTP errors\n  AuthenticationError,\n  ValidationError,\n  NotFoundError,\n  ConflictError,\n  RateLimitError,\n  ServerError,\n\n  // Connection errors\n  ConnectionError,\n  TimeoutError,\n\n  // SDK errors\n  ConfigurationError,\n  PollingTimeoutError,\n  InvoiceProcessingError,\n\n  // Error factory\n  ErrorFactory,\n\n  // Type guards\n  isNfeError,\n  isAuthenticationError,\n  isValidationError,\n  isNotFoundError,\n  isConnectionError,\n  isTimeoutError,\n  isPollingTimeoutError,\n\n  // Legacy aliases (v2 compatibility)\n  BadRequestError,\n  APIError,\n  InternalServerError,\n\n  // Error types\n  ErrorTypes,\n  type ErrorType,\n} from './core/errors/index.js';\n\n// ============================================================================\n// Certificate Validator\n// ============================================================================\n\n/**\n * Certificate validation utilities\n *\n * @see {@link CertificateValidator} - Certificate validation utility class\n *\n * @example\n * ```typescript\n * import { CertificateValidator } from 'nfe-io';\n *\n * const validation = await CertificateValidator.validate(certBuffer, 'password');\n * if (validation.valid) {\n *   console.log('Certificate expires:', validation.metadata?.validTo);\n * }\n * ```\n */\nexport { CertificateValidator } from './core/utils/certificate-validator.js';\n\n// ============================================================================\n// Resource Classes (for advanced usage)\n// ============================================================================\n\n/**\n * Transportation Invoices (CT-e) Resource\n *\n * @see {@link TransportationInvoicesResource} - CT-e operations via Distribuição DFe\n *\n * @example\n * ```typescript\n * import { TransportationInvoicesResource } from 'nfe-io';\n *\n * // For advanced usage when extending the SDK\n * class CustomCteResource extends TransportationInvoicesResource {\n *   // Add custom methods\n * }\n * ```\n */\nexport { TransportationInvoicesResource } from './core/resources/transportation-invoices.js';\nexport { TaxCalculationResource, createTaxCalculationResource } from './core/resources/tax-calculation.js';\nexport { TaxCodesResource, createTaxCodesResource } from './core/resources/tax-codes.js';\nexport { ProductInvoicesResource } from './core/resources/product-invoices.js';\nexport { StateTaxesResource } from './core/resources/state-taxes.js';\nexport { ServiceInvoicesRtcResource } from './core/resources/service-invoices-rtc.js';\nexport { ProductInvoicesRtcResource } from './core/resources/product-invoices-rtc.js';\nexport { MunicipalTaxesResource } from './core/resources/municipal-taxes.js';\nexport { ConsumerInvoicesResource } from './core/resources/consumer-invoices.js';\nexport type {\n  ConsumerInvoiceListOptions,\n  ConsumerInvoiceEnvironment,\n  // Parâmetro de `getItems`/`getEvents`: aparecia na assinatura pública sem ser\n  // importável, então o chamador não conseguia nomear o próprio argumento.\n  ConsumerInvoicePageOptions,\n} from './core/resources/consumer-invoices.js';\n\n// Retorno de `companies.getCertificateStatus()`. Mesmo motivo: estava na\n// assinatura pública e fora da lista de exports.\nexport type { CertificateStatusSummary } from './core/resources/companies.js';\nexport { CertificatesResource } from './core/resources/certificates.js';\nexport { NotificationsResource } from './core/resources/notifications.js';\nexport type { Notification, NotificationListResponse } from './core/resources/notifications.js';\nexport type {\n  CreateInvoiceResponse,\n  CancelInvoiceResponse,\n} from './core/resources/service-invoices.js';\n\n// ============================================================================\n// Default Export (maintains v2 compatibility)\n// ============================================================================\n\n/**\n * Default export for CommonJS compatibility\n *\n * @description\n * Allows both ES modules and CommonJS usage:\n *\n * @example ES Modules\n * ```typescript\n * import { NfeClient } from 'nfe-io';\n * const nfe = new NfeClient({ apiKey: 'xxx' });\n * ```\n *\n * @example ES Modules (default import)\n * ```typescript\n * import nfeFactory from 'nfe-io';\n * const nfe = nfeFactory({ apiKey: 'xxx' });\n * ```\n *\n * @example CommonJS\n * ```javascript\n * const { NfeClient } = require('nfe-io');\n * const nfe = new NfeClient({ apiKey: 'xxx' });\n * ```\n *\n * @example CommonJS (default require)\n * ```javascript\n * const nfeFactory = require('nfe-io').default;\n * const nfe = nfeFactory({ apiKey: 'xxx' });\n * ```\n */\nimport nfeFactory from './core/client.js';\nimport { PACKAGE_NAME as PKG_NAME, VERSION as PKG_VERSION } from './version.js';\nexport default nfeFactory;\n\n// ============================================================================\n// Package Information\n// ============================================================================\n\n/**\n * NPM package name\n *\n * Vem de `src/version.ts`, gerado do `package.json`. Até 2026-09-02 esta constante\n * dizia `@nfe-io/sdk` — pacote que não existe; o publicado é `nfe-io`.\n *\n * @constant\n */\nexport const PACKAGE_NAME = PKG_NAME;\n\n/**\n * Current SDK version\n *\n * Vem da mesma fonte. NÃO fixar literal: até 2026-09-02 esta constante dizia\n * `5.1.0`, `VERSION` dizia o mesmo, o `package.json` dizia `5.2.0` e o User-Agent\n * dizia `3.0.0` — quatro valores para uma informação só.\n *\n * @constant\n */\nexport const PACKAGE_VERSION = PKG_VERSION;\n\n/**\n * NFE.io API version supported by this SDK\n * @constant\n */\nexport const API_VERSION = 'v1';\n\n/**\n * GitHub repository URL\n * @constant\n */\nexport const REPOSITORY_URL = 'https://github.com/nfe/client-nodejs';\n\n/**\n * Official NFE.io API documentation URL\n * @constant\n */\nexport const DOCUMENTATION_URL = 'https://nfe.io/docs';\n\n// ============================================================================\n// Environment Detection & Utilities\n// ============================================================================\n\n/**\n * Check if the current environment supports NFE.io SDK v3 requirements\n *\n * @description\n * Validates that the runtime environment has all necessary features:\n * - Node.js 18+ (for native fetch support)\n * - Fetch API availability\n * - AbortController availability\n *\n * @returns Object containing support status and detected issues\n *\n * @example\n * ```typescript\n * const check = isEnvironmentSupported();\n * if (!check.supported) {\n *   console.error('Environment issues:', check.issues);\n *   console.error('Node version:', check.nodeVersion);\n * }\n * ```\n */\nexport function isEnvironmentSupported(): {\n  /** Whether all requirements are met */\n  supported: boolean;\n  /** Detected Node.js version (e.g., \"v18.17.0\") */\n  nodeVersion?: string;\n  /** Whether Fetch API is available */\n  hasFetch: boolean;\n  /** Whether AbortController is available */\n  hasAbortController: boolean;\n  /** List of detected compatibility issues */\n  issues: string[];\n} {\n  const issues: string[] = [];\n  let nodeVersion: string | undefined;\n\n  // Check Node.js version\n  try {\n    nodeVersion = (globalThis as any).process?.version;\n    if (nodeVersion) {\n      const majorVersion = parseInt(nodeVersion.slice(1).split('.')[0]!);\n      if (majorVersion < 18) {\n        issues.push(`Node.js ${majorVersion} is not supported. Requires Node.js 18+.`);\n      }\n    }\n  } catch {\n    issues.push('Unable to detect Node.js version');\n  }\n\n  // Check fetch support\n  const hasFetch = typeof fetch !== 'undefined';\n  if (!hasFetch) {\n    issues.push('Fetch API not available');\n  }\n\n  // Check AbortController support\n  const hasAbortController = typeof AbortController !== 'undefined';\n  if (!hasAbortController) {\n    issues.push('AbortController not available');\n  }\n\n  const result: {\n    supported: boolean;\n    nodeVersion?: string;\n    hasFetch: boolean;\n    hasAbortController: boolean;\n    issues: string[];\n  } = {\n    supported: issues.length === 0,\n    hasFetch,\n    hasAbortController,\n    issues,\n  };\n\n  if (nodeVersion) {\n    result.nodeVersion = nodeVersion;\n  }\n\n  return result;\n}\n\n/**\n * Get comprehensive SDK runtime information\n *\n * @description\n * Returns detailed information about the current runtime environment,\n * useful for debugging and support.\n *\n * @returns Object containing SDK and runtime environment information\n *\n * @example\n * ```typescript\n * const info = getRuntimeInfo();\n * console.log('SDK Version:', info.sdkVersion);\n * console.log('Node Version:', info.nodeVersion);\n * console.log('Platform:', info.platform);\n * console.log('Environment:', info.environment);\n * ```\n */\nexport function getRuntimeInfo(): {\n  /** Current SDK version */\n  sdkVersion: string;\n  /** Node.js version (e.g., \"v18.17.0\") */\n  nodeVersion: string;\n  /** Operating system platform (e.g., \"linux\", \"darwin\", \"win32\") */\n  platform: string;\n  /** CPU architecture (e.g., \"x64\", \"arm64\") */\n  arch: string;\n  /** Runtime environment type */\n  environment: 'node' | 'browser' | 'unknown';\n} {\n  let nodeVersion = 'unknown';\n  let platform = 'unknown';\n  let arch = 'unknown';\n  let environment: 'node' | 'browser' | 'unknown' = 'unknown';\n\n  try {\n    const process = (globalThis as any).process;\n    if (process) {\n      nodeVersion = process.version || 'unknown';\n      platform = process.platform || 'unknown';\n      arch = process.arch || 'unknown';\n      environment = 'node';\n    } else if (typeof window !== 'undefined' && typeof (window as any).navigator !== 'undefined') {\n      environment = 'browser';\n      platform = (window as any).navigator.platform || 'unknown';\n    }\n  } catch {\n    // Safe fallback\n  }\n\n  return {\n    sdkVersion: PACKAGE_VERSION,\n    nodeVersion,\n    platform,\n    arch,\n    environment,\n  };\n}\n\n// ============================================================================\n// Quick Start Helpers\n// ============================================================================\n\n/**\n * Create NFE.io client from environment variable\n *\n * @description\n * Convenience function that reads API key from NFE_API_KEY environment variable.\n * Useful for serverless functions and quick prototyping.\n *\n * @param environment - Target environment ('production' or 'sandbox')\n * @returns Configured NfeClient instance\n * @throws {ConfigurationError} If NFE_API_KEY environment variable is not set\n *\n * @example\n * ```typescript\n * // Set environment variable: NFE_API_KEY=your-api-key\n * const nfe = createClientFromEnv('production');\n *\n * // Use the client normally\n * const companies = await nfe.companies.list();\n * ```\n *\n * @example Docker/Kubernetes\n * ```yaml\n * env:\n *   - name: NFE_API_KEY\n *     valueFrom:\n *       secretKeyRef:\n *         name: nfe-credentials\n *         key: api-key\n * ```\n */\nexport function createClientFromEnv(environment?: 'production' | 'sandbox') {\n  const apiKey = (globalThis as any).process?.env?.NFE_API_KEY;\n  if (!apiKey) {\n    const { ConfigurationError } = require('./core/errors');\n    throw new ConfigurationError(\n      'NFE_API_KEY environment variable is required when using createClientFromEnv()'\n    );\n  }\n\n  const { NfeClient } = require('./core/client');\n  return new NfeClient({\n    apiKey,\n    environment: environment || 'production'\n  });\n}\n\n/**\n * Validate NFE.io API key format\n *\n * @description\n * Performs basic validation on API key format before attempting to use it.\n * Helps catch common mistakes like missing keys or keys with whitespace.\n *\n * @param apiKey - The API key to validate\n * @returns Validation result with any detected issues\n *\n * @example\n * ```typescript\n * const result = validateApiKeyFormat('my-api-key');\n * if (!result.valid) {\n *   console.error('API key issues:', result.issues);\n *   // [\"API key appears to be too short\"]\n * }\n * ```\n *\n * @example Integration with client\n * ```typescript\n * const apiKey = process.env.NFE_API_KEY;\n * const validation = validateApiKeyFormat(apiKey);\n *\n * if (!validation.valid) {\n *   throw new Error(`Invalid API key: ${validation.issues.join(', ')}`);\n * }\n *\n * const nfe = new NfeClient({ apiKey });\n * ```\n */\nexport function validateApiKeyFormat(apiKey: string): {\n  /** Whether the API key passes basic validation */\n  valid: boolean;\n  /** List of validation issues found */\n  issues: string[];\n} {\n  const issues: string[] = [];\n\n  if (!apiKey) {\n    issues.push('API key is required');\n  } else {\n    if (apiKey.length < 10) {\n      issues.push('API key appears to be too short');\n    }\n\n    if (apiKey.includes(' ')) {\n      issues.push('API key should not contain spaces');\n    }\n\n    // Add more validation rules as needed\n  }\n\n  return {\n    valid: issues.length === 0,\n    issues,\n  };\n}\n"],"mappings":"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"}