Cómo configurar servidores proxy para renderizado PDF en C

This article was translated from English: Does it need improvement?
Translated
View the article in English

La configuración de proxy en IronPDF es un parámetro de método en sobrecargas de RenderHtmlAsPdf() — no es una propiedad en ChromePdfRenderOptions. Esta distinción es importante porque RenderHtmlAsPdf() no tiene ningún parámetro de proxy en absoluto, lo que requiere una estrategia diferente cuando necesitas renderizar URLs en vivo detrás de un proxy corporativo. Si pasas null (el valor predeterminado), IronPDF se conecta directamente.

Esta guía cubre cada escenario de proxy que encontrarás en producción: cadenas de proxy directas, proxies corporativos autenticados, la solución RenderUrlAsPdf, configuración de contenedores Docker, integración de canalizaciones CI/CD y patrones comunes de solución de problemas para intercepción SSL y autenticación NTLM.

Configuración de proxy en entornos empresariales españoles

En España, la configuración de proxy es especialmente relevante en dos contextos:

AWS eu-south-2 (Madrid) y acceso a servicios de la AEAT: Las aplicaciones que generan PDFs mediante IronPDF y acceden a la sede electrónica de la AEAT — por ejemplo, para validar facturas VERI*FACTU o procesar documentos del portal — pueden necesitar configurar un proxy corporativo cuando se despliegan en entornos de red corporativos dentro de AWS eu-south-2. El patrón HttpClient + WebProxy descrito en esta guía es el más adecuado para este escenario, ya que permite controlar exactamente qué peticiones HTTP pasan por el proxy.

Sector bancario español y proxies corporativos: Los equipos de desarrollo en entidades financieras españolas que integran IronPDF en aplicaciones de generación de documentos (extractos bancarios, contratos, documentación regulatoria para el Banco de España) operan habitualmente detrás de proxies corporativos con autenticación NTLM o BASIC. Esta guía cubre ambos métodos de autenticación.

Para aplicaciones de Facturae o SII (Suministro Inmediato de Información) que realizan peticiones HTTP a servicios externos a través de un proxy, la configuración correcta del WebProxy en HttpClient es fundamental para garantizar que las llamadas a la AEAT y a los servicios de TicketBAI de las Haciendas Forales de Bizkaia, Gipuzkoa y Araba funcionen correctamente en redes corporativas.

Comience una prueba gratuita de 30 días para probar configuraciones de proxy en su entorno.

Inicio rápido: Renderizar PDFs a través de un Proxy

El parámetro opcional proxy de IronPDF te ayuda a convertir páginas web en vivo servidas detrás de proxies corporativos. Use este fragmento de código para comenzar rápidamente.

  1. Instala IronPDF con el Administrador de Paquetes NuGet

    PM > Install-Package IronPdf
  2. Copie y ejecute este fragmento de código.

    using IronPdf;
    
    var renderer = new ChromePdfRenderer();
    
    // Proxy is the third parameter — not a render option
    PdfDocument pdf = renderer.RenderHtmlAsPdf(
        "<h1>Hello from behind the proxy</h1>",
        baseUrlOrPath: null,
        proxy: "http://proxy.corp.local:8080"
    );
    pdf.SaveAs("proxied-output.pdf");
  3. Despliegue para probar en su entorno real

    Comienza a usar IronPDF en tu proyecto hoy mismo con una prueba gratuita

    arrow pointer

Flujo de Trabajo Mínimo (3 Pasos)

  1. Instala IronPDF a través de NuGet: Install-Package IronPdf
  2. Pasa la cadena de proxy como el tercer parámetro a RenderHtmlAsPdf
  3. Formato: http(s)://host:port o http(s)://user:pass@host:port para proxies autenticados

¿Cómo se pasa un proxy a RenderHtmlAsPdf?

El parámetro Proxy es un string opcional en cuatro firmas de método:

// Instance methods
PdfDocument RenderHtmlAsPdf(string Html, string BaseUrlOrPath, string Proxy = null)
PdfDocument RenderHtmlAsPdf(string Html, Uri BaseUrl = null, string Proxy = null)

// Static methods
PdfDocument StaticRenderHtmlAsPdf(string Html, ChromePdfRenderOptions Options = null, string Proxy = null)
PdfDocument StaticRenderHtmlAsPdf(string Html, string BaseUrlOrPath, ChromePdfRenderOptions Options = null, string Proxy = null)
// Instance methods
PdfDocument RenderHtmlAsPdf(string Html, string BaseUrlOrPath, string Proxy = null)
PdfDocument RenderHtmlAsPdf(string Html, Uri BaseUrl = null, string Proxy = null)

// Static methods
PdfDocument StaticRenderHtmlAsPdf(string Html, ChromePdfRenderOptions Options = null, string Proxy = null)
PdfDocument StaticRenderHtmlAsPdf(string Html, string BaseUrlOrPath, ChromePdfRenderOptions Options = null, string Proxy = null)
' Instance methods
Function RenderHtmlAsPdf(Html As String, BaseUrlOrPath As String, Optional Proxy As String = Nothing) As PdfDocument
End Function

Function RenderHtmlAsPdf(Html As String, Optional BaseUrl As Uri = Nothing, Optional Proxy As String = Nothing) As PdfDocument
End Function

' Static methods
Shared Function StaticRenderHtmlAsPdf(Html As String, Optional Options As ChromePdfRenderOptions = Nothing, Optional Proxy As String = Nothing) As PdfDocument
End Function

Shared Function StaticRenderHtmlAsPdf(Html As String, BaseUrlOrPath As String, Optional Options As ChromePdfRenderOptions = Nothing, Optional Proxy As String = Nothing) As PdfDocument
End Function
$vbLabelText   $csharpLabel

Cuando este parámetro es null (el valor predeterminado), el motor Chromium de IronPDF se conecta directamente a recursos externos — hojas de estilo, imágenes, fuentes y archivos JavaScript referenciados en tu HTML. Cuando proporciona una cadena de proxy, todas las solicitudes HTTP/HTTPS del motor de renderizado se enrutan a través de ese proxy.

using IronPdf;

var renderer = new ChromePdfRenderer();

// Direct connection (default — no proxy)
var pdfDirect = renderer.RenderHtmlAsPdf("<h1>Direct</h1>");

// Through an unauthenticated proxy
var pdfProxied = renderer.RenderHtmlAsPdf(
    "<h1>Proxied</h1>",
    baseUrlOrPath: null,
    proxy: "http://squid.internal:3128"
);

// Using the Uri overload
var pdfUri = renderer.RenderHtmlAsPdf(
    "<h1>Proxied via Uri overload</h1>",
    baseUrl: new Uri("https://assets.example.com/"),
    proxy: "https://proxy.corp.local:8443"
);
using IronPdf;

var renderer = new ChromePdfRenderer();

// Direct connection (default — no proxy)
var pdfDirect = renderer.RenderHtmlAsPdf("<h1>Direct</h1>");

// Through an unauthenticated proxy
var pdfProxied = renderer.RenderHtmlAsPdf(
    "<h1>Proxied</h1>",
    baseUrlOrPath: null,
    proxy: "http://squid.internal:3128"
);

// Using the Uri overload
var pdfUri = renderer.RenderHtmlAsPdf(
    "<h1>Proxied via Uri overload</h1>",
    baseUrl: new Uri("https://assets.example.com/"),
    proxy: "https://proxy.corp.local:8443"
);
Imports IronPdf

Dim renderer As New ChromePdfRenderer()

' Direct connection (default — no proxy)
Dim pdfDirect = renderer.RenderHtmlAsPdf("<h1>Direct</h1>")

' Through an unauthenticated proxy
Dim pdfProxied = renderer.RenderHtmlAsPdf(
    "<h1>Proxied</h1>",
    baseUrlOrPath:=Nothing,
    proxy:="http://squid.internal:3128"
)

' Using the Uri overload
Dim pdfUri = renderer.RenderHtmlAsPdf(
    "<h1>Proxied via Uri overload</h1>",
    baseUrl:=New Uri("https://assets.example.com/"),
    proxy:="https://proxy.corp.local:8443"
)
$vbLabelText   $csharpLabel

La cadena de proxy admite tanto esquemas http:// como https://. Utiliza https:// cuando el propio proxy requiere cifrado TLS para la conexión entre tu aplicación y el servidor proxy. El esquema aquí se refiere a la conexión proxy, no al recurso final — un proxy http:// aún puede obtener recursos https:// a través de túneles CONNECT.

Las variantes de método estático aceptan el mismo parámetro de proxy, lo cual es útil para renders puntuales en aplicaciones de consola o pruebas unitarias:

// Static render with proxy — no renderer instance needed
var pdf = ChromePdfRenderer.StaticRenderHtmlAsPdf(
    "<h1>Static render through proxy</h1>",
    options: null,
    proxy: "http://proxy.corp.local:8080"
);
// Static render with proxy — no renderer instance needed
var pdf = ChromePdfRenderer.StaticRenderHtmlAsPdf(
    "<h1>Static render through proxy</h1>",
    options: null,
    proxy: "http://proxy.corp.local:8080"
);
' Static render with proxy — no renderer instance needed
Dim pdf = ChromePdfRenderer.StaticRenderHtmlAsPdf(
    "<h1>Static render through proxy</h1>",
    options:=Nothing,
    proxy:="http://proxy.corp.local:8080"
)
$vbLabelText   $csharpLabel

Importante: No hay propiedad Proxy en ChromePdfRenderOptions. No lo busque allí. El proxy es estrictamente un parámetro de método en sobrecargas de RenderHtmlAsPdf y FromHtml.

¿Cómo se autentica con un proxy corporativo?

La mayoría de los proxies empresariales requieren credenciales. Los incrustas directamente en la URL de proxy usando el formato http(s)://username:password@host:port:

using IronPdf;

var renderer = new ChromePdfRenderer();

string proxyWithAuth = "http://svc-account:P%40ssw0rd%21@proxy.corp.local:8080";

PdfDocument pdf = renderer.RenderHtmlAsPdf(
    htmlContent,
    baseUrlOrPath: @"C:\templates\assets\",
    proxy: proxyWithAuth
);
pdf.SaveAs("report.pdf");
using IronPdf;

var renderer = new ChromePdfRenderer();

string proxyWithAuth = "http://svc-account:P%40ssw0rd%21@proxy.corp.local:8080";

PdfDocument pdf = renderer.RenderHtmlAsPdf(
    htmlContent,
    baseUrlOrPath: @"C:\templates\assets\",
    proxy: proxyWithAuth
);
pdf.SaveAs("report.pdf");
Imports IronPdf

Dim renderer As New ChromePdfRenderer()

Dim proxyWithAuth As String = "http://svc-account:P%40ssw0rd%21@proxy.corp.local:8080"

Dim pdf As PdfDocument = renderer.RenderHtmlAsPdf(
    htmlContent,
    baseUrlOrPath: "C:\templates\assets\",
    proxy:=proxyWithAuth
)
pdf.SaveAs("report.pdf")
$vbLabelText   $csharpLabel

Codifica en URL los caracteres especiales en las contraseñas. Si tu contraseña contiene @, #, :, /, u otros caracteres reservados URI, deben estar codificados en porcentaje. Codificaciones comunes:

Carácter Codificado
@ %40
# %23
: %3A
/ %2F
! %21
% %25

Utiliza Uri.EscapeDataString() para codificar la contraseña de manera programática:

string rawPassword = "P@ssw0rd!";
string encoded = Uri.EscapeDataString(rawPassword); // "P%40ssw0rd%21"
string proxy = $"http://svc-account:{encoded}@proxy.corp.local:8080";
string rawPassword = "P@ssw0rd!";
string encoded = Uri.EscapeDataString(rawPassword); // "P%40ssw0rd%21"
string proxy = $"http://svc-account:{encoded}@proxy.corp.local:8080";
Imports System

Dim rawPassword As String = "P@ssw0rd!"
Dim encoded As String = Uri.EscapeDataString(rawPassword) ' "P%40ssw0rd%21"
Dim proxy As String = $"http://svc-account:{encoded}@proxy.corp.local:8080"
$vbLabelText   $csharpLabel

No confundas la autenticación del proxy con la autenticación de la página web. Las propiedades ChromeHttpLoginCredentials.NetworkUsername y NetworkPassword autentican contra la página web que se está renderizando (NTLM/Negotiate con un sitio web), no contra un servidor proxy. Para la autenticación de proxy, las credenciales van en la cadena URL del proxy como se muestra arriba.

¿Cómo representar URLs detrás de un proxy?

RenderUrlToPdf no acepta un parámetro de proxy. Esta es una elección deliberada de diseño de API — NavigateUrl navega Chromium a una URL, y la configuración del proxy para esa navegación se maneja de manera diferente que para la carga de recursos durante la renderización de HTML.

La solución recomendada: obtén el HTML tú mismo usando HttpClient configurado con un HttpProxy, luego pasa la cadena HTML a RenderHtmlAsPdf con el parámetro de proxy (para que los recursos referenciados — imágenes, CSS, fuentes — también se enruten a través del proxy).

using IronPdf;
using System.Net;
using System.Net.Http;

// Step 1: Configure HttpClient with the corporate proxy
var proxy = new WebProxy("http://proxy.corp.local:8080")
{
    Credentials = new NetworkCredential("svc-account", "P@ssw0rd!")
};

var handler = new HttpClientHandler { Proxy = proxy, UseProxy = true };
using var httpClient = new HttpClient(handler);

// Step 2: Fetch the HTML from the target URL
string targetUrl = "https://dashboard.internal.corp/quarterly-report";
string html = await httpClient.GetStringAsync(targetUrl);

// Step 3: Render the fetched HTML, with the proxy for asset loading
var renderer = new ChromePdfRenderer();

PdfDocument pdf = renderer.RenderHtmlAsPdf(
    html,
    baseUrlOrPath: targetUrl,  // Resolves relative asset paths against the original URL
    proxy: "http://svc-account:P%40ssw0rd%21@proxy.corp.local:8080"
);
pdf.SaveAs("quarterly-report.pdf");
using IronPdf;
using System.Net;
using System.Net.Http;

// Step 1: Configure HttpClient with the corporate proxy
var proxy = new WebProxy("http://proxy.corp.local:8080")
{
    Credentials = new NetworkCredential("svc-account", "P@ssw0rd!")
};

var handler = new HttpClientHandler { Proxy = proxy, UseProxy = true };
using var httpClient = new HttpClient(handler);

// Step 2: Fetch the HTML from the target URL
string targetUrl = "https://dashboard.internal.corp/quarterly-report";
string html = await httpClient.GetStringAsync(targetUrl);

// Step 3: Render the fetched HTML, with the proxy for asset loading
var renderer = new ChromePdfRenderer();

PdfDocument pdf = renderer.RenderHtmlAsPdf(
    html,
    baseUrlOrPath: targetUrl,  // Resolves relative asset paths against the original URL
    proxy: "http://svc-account:P%40ssw0rd%21@proxy.corp.local:8080"
);
pdf.SaveAs("quarterly-report.pdf");
Imports IronPdf
Imports System.Net
Imports System.Net.Http

' Step 1: Configure HttpClient with the corporate proxy
Dim proxy As New WebProxy("http://proxy.corp.local:8080") With {
    .Credentials = New NetworkCredential("svc-account", "P@ssw0rd!")
}

Dim handler As New HttpClientHandler With {.Proxy = proxy, .UseProxy = True}
Using httpClient As New HttpClient(handler)
    ' Step 2: Fetch the HTML from the target URL
    Dim targetUrl As String = "https://dashboard.internal.corp/quarterly-report"
    Dim html As String = Await httpClient.GetStringAsync(targetUrl)

    ' Step 3: Render the fetched HTML, with the proxy for asset loading
    Dim renderer As New ChromePdfRenderer()

    Dim pdf As PdfDocument = renderer.RenderHtmlAsPdf(
        html,
        baseUrlOrPath:=targetUrl,  ' Resolves relative asset paths against the original URL
        proxy:="http://svc-account:P%40ssw0rd%21@proxy.corp.local:8080"
    )
    pdf.SaveAs("quarterly-report.pdf")
End Using
$vbLabelText   $csharpLabel

El parámetro baseUrlOrPath se establece en la URL objetivo original para que las rutas relativas en el HTML obtenido (<img src="/images/logo.png">, <link href="/css/styles.css">) se resuelvan correctamente. El parámetro proxy asegura que esas solicitudes de recursos se enruten a través del proxy durante la renderización.

Este patrón también funciona con páginas detrás de autenticación — configura el HttpClient con las cookies o encabezados apropiados antes de obtener el HTML autenticado, luego pásalo a IronPDF. El cómo configurar el encabezado de solicitud HTTP cubre la configuración de encabezados para solicitudes autenticadas.

Si la página depende de JavaScript para la renderización (SPAs, paneles de React, aplicaciones de Angular), el HTML obtenido solo contendrá el shell inicial — la renderización del lado del cliente no se ejecutará durante la obtención HttpClient. Para esos casos, tienes dos opciones: establece variables de entorno a nivel de sistema HTTPS_PROXY (cubiertas en la siguiente sección) para que RenderUrlAsPdf() se enrute a través del proxy a nivel del sistema operativo, o utiliza un navegador sin cabeza para obtener el HTML completamente renderizado antes de pasarlo a RenderHtmlAsPdf().

¿Cómo configurar un proxy en contenedores Docker?

En entornos containerizados, puedes preferir la configuración de proxy a nivel del sistema sobre los parámetros por método. El motor Chromium de IronPDF respeta las variables de entorno estándar HTTP_PROXY y HTTPS_PROXY que los contenedores de Linux usan para el enrutamiento de tráfico saliente.

Establece estas en tu Dockerfile:

FROM mcr.microsoft.com/dotnet/aspnet:8.0

# System-level proxy for all outbound HTTP/HTTPS traffic
ENV HTTP_PROXY=http://proxy.corp.local:8080
ENV HTTPS_PROXY=http://proxy.corp.local:8080
ENV NO_PROXY=localhost,127.0.0.1,.internal.corp

# Install IronPDF dependencies (fonts, etc.)
RUN apt-get update && apt-get install -y \
    libgdiplus \
    libc6-dev \
    fonts-liberation \
    && rm -rf /var/lib/apt/lists/*

WORKDIR /app
COPY --from=build /app/publish .
ENTRYPOINT ["dotnet", "MyApp.dll"]

Con estas variables de entorno configuradas, puedes llamar a RenderHtmlAsPdf sin el parámetro de proxy — Chromium recoge la configuración a nivel de sistema automáticamente:

// No proxy parameter needed — Chromium uses HTTP_PROXY env var
var renderer = new ChromePdfRenderer();
var pdf = renderer.RenderHtmlAsPdf(htmlContent);
// No proxy parameter needed — Chromium uses HTTP_PROXY env var
var renderer = new ChromePdfRenderer();
var pdf = renderer.RenderHtmlAsPdf(htmlContent);
' No proxy parameter needed — Chromium uses HTTP_PROXY env var
Dim renderer As New ChromePdfRenderer()
Dim pdf = renderer.RenderHtmlAsPdf(htmlContent)
$vbLabelText   $csharpLabel

RenderHtmlAsPdf() es importante para recursos internos. Sin ella, las solicitudes a servicios internos (como un servidor CSS local o un CDN de imágenes que se ejecuta dentro de tu clúster de Kubernetes) se encaminarían innecesariamente a través del proxy. Separa con comas los nombres de host y dominios que deben eludir el proxy.

Si necesitas un proxy a nivel del sistema para el tráfico general y un proxy diferente para renders específicos, el parámetro del método tiene prioridad sobre la variable de entorno. Esto te da control por renderizado cuando es necesario.

Configuración ENS para contenedores en la Administración Pública española

Las aplicaciones que procesan documentos para la Administración Pública española bajo el Esquema Nacional de Seguridad (ENS) tienen requisitos adicionales en la configuración del proxy, especialmente en el nivel ENS Alto y ENS Medio. Para despliegues que generan PDFs de expedientes electrónicos, notificaciones o documentación regulatoria, considera los siguientes patrones:

Aislamiento de red en despliegues ENS: Los contenedores que procesan información con clasificación ENS no deben enrutar tráfico a través de proxies públicos. Configura NO_PROXY explícitamente para que todo el tráfico a servicios internos de la administración bypasee el proxy corporativo:

FROM mcr.microsoft.com/dotnet/aspnet:8.0

# Configuración ENS: proxy sólo para tráfico externo
ENV HTTP_PROXY=http://proxy.corpgov.administracion.es:8080
ENV HTTPS_PROXY=http://proxy.corpgov.administracion.es:8080
# Excluir redes internas de la administración
ENV NO_PROXY=localhost,127.0.0.1,.administracion.es,.gob.es,.hacienda.es,.aeat.es,.face.gob.es

WORKDIR /app
COPY --from=build /app/publish .
ENTRYPOINT ["dotnet", "DocumentosENS.dll"]

Certificados ENS y proxies MITM: Muchos proxies corporativos en la Administración Pública española realizan inspección SSL con certificados emitidos por la FNMT-RCM (Fábrica Nacional de Moneda y Timbre) u otras CAs de confianza del Estado. Para que IronPDF confíe en estos certificados:

# En el contenedor (Ubuntu/Debian)
COPY fnmt-root-ca.crt /usr/local/share/ca-certificates/
RUN update-ca-certificates
# En el contenedor (Ubuntu/Debian)
COPY fnmt-root-ca.crt /usr/local/share/ca-certificates/
RUN update-ca-certificates
SHELL

AWS eu-south-2 con ENS: Para despliegues en AWS eu-south-2 que deben cumplir con ENS, configura Security Groups y NACLs para permitir únicamente el tráfico de salida hacia los endpoints aprobados de la AEAT, FACe, y servicios de TicketBAI de Bizkaia, Gipuzkoa y Araba. El proxy actúa como punto de control adicional para registrar y auditar las peticiones de generación de documentos — requisito habitual en el perfil de cumplimiento ENS Medio y Alto.

¿Cómo manejar un proxy en las pipelines CI/CD?

Los runners de CI/CD en redes corporativas frecuentemente se encuentran detrás de proxies. Pasa la URL del proxy como una variable de compilación o secreto — nunca codifiques credenciales en el control de versiones.

GitHub Actions:

jobs:
  generate-pdf:
    runs-on: ubuntu-latest
    env:
      HTTP_PROXY: ${{ secrets.CORP_PROXY_URL }}
      HTTPS_PROXY: ${{ secrets.CORP_PROXY_URL }}
    steps:
      - uses: actions/checkout@v4
      - run: dotnet build
      - run: dotnet test
jobs:
  generate-pdf:
    runs-on: ubuntu-latest
    env:
      HTTP_PROXY: ${{ secrets.CORP_PROXY_URL }}
      HTTPS_PROXY: ${{ secrets.CORP_PROXY_URL }}
    steps:
      - uses: actions/checkout@v4
      - run: dotnet build
      - run: dotnet test
YAML

Azure DevOps:

variables:
  - group: proxy-settings  # Contains PROXY_URL secret

steps:
  - script: |
      export HTTP_PROXY=$(PROXY_URL)
      export HTTPS_PROXY=$(PROXY_URL)
      dotnet run --project PdfGenerator
    displayName: 'Generate PDFs behind proxy'
variables:
  - group: proxy-settings  # Contains PROXY_URL secret

steps:
  - script: |
      export HTTP_PROXY=$(PROXY_URL)
      export HTTPS_PROXY=$(PROXY_URL)
      dotnet run --project PdfGenerator
    displayName: 'Generate PDFs behind proxy'
YAML

Jenkins (Pipeline Declarativo):

environment {
    HTTP_PROXY  = credentials('corp-proxy-url')
    HTTPS_PROXY = credentials('corp-proxy-url')
}

En los tres casos, Chromium lee las variables de entorno automáticamente. Si prefieres un control explícito, lee la URL del proxy desde el entorno y pásala como el parámetro del método:

string? proxy = Environment.GetEnvironmentVariable("HTTPS_PROXY");
var pdf = renderer.RenderHtmlAsPdf(html, baseUrlOrPath: null, proxy: proxy);
string? proxy = Environment.GetEnvironmentVariable("HTTPS_PROXY");
var pdf = renderer.RenderHtmlAsPdf(html, baseUrlOrPath: null, proxy: proxy);
Option Strict On



Dim proxy As String = Environment.GetEnvironmentVariable("HTTPS_PROXY")
Dim pdf = renderer.RenderHtmlAsPdf(html, baseUrlOrPath:=Nothing, proxy:=proxy)
$vbLabelText   $csharpLabel

Configuración de proxy para pipelines de facturación electrónica española

Las empresas españolas que integran IronPDF en flujos de facturación electrónica necesitan configurar el proxy correctamente para acceder a los servicios externos de la AEAT y las Haciendas Forales.

VERI*FACTU y acceso a servicios de la AEAT

El sistema VERI*FACTU exige que los sistemas de facturación envíen registros de facturación a la sede electrónica de la AEAT en tiempo real. Cuando IronPDF genera los PDFs de las facturas en un entorno corporativo con proxy, debes asegurarte de que las peticiones al endpoint de la AEAT (https://prewww2.aeat.es/... en preproducción, https://www7.aeat.es/... en producción) no queden bloqueadas:

using IronPdf;
using System.Net;
using System.Net.Http;

// Proxy corporativo para acceder a AEAT VERI*FACTU
var proxy = new WebProxy("http://proxy.corp.empresa.es:8080")
{
    Credentials = new NetworkCredential("usuario_srv", "contraseña")
};

var handler = new HttpClientHandler { Proxy = proxy, UseProxy = true };
using var httpClient = new HttpClient(handler);

// Verificación de conectividad con AEAT antes de generar PDF
var response = await httpClient.GetAsync("https://www7.aeat.es/wlpl/TIKE-CONT/ws/SistemaFacturacion/VerifactuSOAP");

// Generar PDF de factura VERI*FACTU
var renderer = new ChromePdfRenderer();
var facturaHtml = await httpClient.GetStringAsync(urlFacturaInterna);
var pdf = renderer.RenderHtmlAsPdf(
    facturaHtml,
    baseUrlOrPath: urlFacturaInterna,
    proxy: "http://usuario_srv:contrase%C3%B1a@proxy.corp.empresa.es:8080"
);
pdf.SaveAs($"factura-verifactu-{numeroFactura}.pdf");
using IronPdf;
using System.Net;
using System.Net.Http;

// Proxy corporativo para acceder a AEAT VERI*FACTU
var proxy = new WebProxy("http://proxy.corp.empresa.es:8080")
{
    Credentials = new NetworkCredential("usuario_srv", "contraseña")
};

var handler = new HttpClientHandler { Proxy = proxy, UseProxy = true };
using var httpClient = new HttpClient(handler);

// Verificación de conectividad con AEAT antes de generar PDF
var response = await httpClient.GetAsync("https://www7.aeat.es/wlpl/TIKE-CONT/ws/SistemaFacturacion/VerifactuSOAP");

// Generar PDF de factura VERI*FACTU
var renderer = new ChromePdfRenderer();
var facturaHtml = await httpClient.GetStringAsync(urlFacturaInterna);
var pdf = renderer.RenderHtmlAsPdf(
    facturaHtml,
    baseUrlOrPath: urlFacturaInterna,
    proxy: "http://usuario_srv:contrase%C3%B1a@proxy.corp.empresa.es:8080"
);
pdf.SaveAs($"factura-verifactu-{numeroFactura}.pdf");
Imports IronPdf
Imports System.Net
Imports System.Net.Http

' Proxy corporativo para acceder a AEAT VERI*FACTU
Dim proxy As New WebProxy("http://proxy.corp.empresa.es:8080") With {
    .Credentials = New NetworkCredential("usuario_srv", "contraseña")
}

Dim handler As New HttpClientHandler With {
    .Proxy = proxy,
    .UseProxy = True
}

Using httpClient As New HttpClient(handler)
    ' Verificación de conectividad con AEAT antes de generar PDF
    Dim response = Await httpClient.GetAsync("https://www7.aeat.es/wlpl/TIKE-CONT/ws/SistemaFacturacion/VerifactuSOAP")

    ' Generar PDF de factura VERI*FACTU
    Dim renderer As New ChromePdfRenderer()
    Dim facturaHtml = Await httpClient.GetStringAsync(urlFacturaInterna)
    Dim pdf = renderer.RenderHtmlAsPdf(
        facturaHtml,
        baseUrlOrPath:=urlFacturaInterna,
        proxy:="http://usuario_srv:contrase%C3%B1a@proxy.corp.empresa.es:8080"
    )
    pdf.SaveAs($"factura-verifactu-{numeroFactura}.pdf")
End Using
$vbLabelText   $csharpLabel

Facturae y acceso a portales B2G

Las empresas que emiten facturas Facturae para la Administración General del Estado utilizan el FACe (Punto General de Entrada de Facturas Electrónicas). En entornos con proxy, configura NO_PROXY para excluir los endpoints internos pero permitir acceso a FACe:

# Docker para pipeline Facturae con proxy corporativo
ENV HTTP_PROXY=http://proxy.corp.empresa.es:8080
ENV HTTPS_PROXY=http://proxy.corp.empresa.es:8080
ENV NO_PROXY=localhost,127.0.0.1,.empresa.es,erp.interno

TicketBAI en las Haciendas Forales: Bizkaia, Gipuzkoa y Araba

TicketBAI es el sistema de facturación obligatorio en el País Vasco. Cada territorio foral tiene su propio endpoint:

  • Bizkaia (Diputación Foral de Bizkaia): https://batuz.eus/QRTBAI/
  • Gipuzkoa (Diputación Foral de Gipuzkoa): https://tbai.egoitza.gipuzkoa.eus/
  • Araba (Diputación Foral de Álava): https://ticketbai.araba.eus/

Para aplicaciones que operan en los tres territorios, configura el proxy con excepciones específicas y valida la conectividad antes del despliegue:

// Validar conectividad TicketBAI por territorio antes de generar PDFs
var territorios = new Dictionary<string, string>
{
    ["Bizkaia"] = "https://batuz.eus/QRTBAI/",
    ["Gipuzkoa"] = "https://tbai.egoitza.gipuzkoa.eus/",
    ["Araba"] = "https://ticketbai.araba.eus/"
};

foreach (var (territorio, endpoint) in territorios)
{
    try
    {
        var resp = await httpClient.GetAsync(endpoint);
        Console.WriteLine($"TicketBAI {territorio}: {resp.StatusCode}");
    }
    catch (Exception ex)
    {
        Console.WriteLine($"TicketBAI {territorio}: Error de proxy - {ex.Message}");
    }
}
// Validar conectividad TicketBAI por territorio antes de generar PDFs
var territorios = new Dictionary<string, string>
{
    ["Bizkaia"] = "https://batuz.eus/QRTBAI/",
    ["Gipuzkoa"] = "https://tbai.egoitza.gipuzkoa.eus/",
    ["Araba"] = "https://ticketbai.araba.eus/"
};

foreach (var (territorio, endpoint) in territorios)
{
    try
    {
        var resp = await httpClient.GetAsync(endpoint);
        Console.WriteLine($"TicketBAI {territorio}: {resp.StatusCode}");
    }
    catch (Exception ex)
    {
        Console.WriteLine($"TicketBAI {territorio}: Error de proxy - {ex.Message}");
    }
}
Imports System
Imports System.Collections.Generic
Imports System.Net.Http

' Validar conectividad TicketBAI por territorio antes de generar PDFs
Dim territorios As New Dictionary(Of String, String) From {
    {"Bizkaia", "https://batuz.eus/QRTBAI/"},
    {"Gipuzkoa", "https://tbai.egoitza.gipuzkoa.eus/"},
    {"Araba", "https://ticketbai.araba.eus/"}
}

For Each kvp In territorios
    Dim territorio As String = kvp.Key
    Dim endpoint As String = kvp.Value
    Try
        Dim resp = Await httpClient.GetAsync(endpoint)
        Console.WriteLine($"TicketBAI {territorio}: {resp.StatusCode}")
    Catch ex As Exception
        Console.WriteLine($"TicketBAI {territorio}: Error de proxy - {ex.Message}")
    End Try
Next
$vbLabelText   $csharpLabel

SII (Suministro Inmediato de Información) y AWS eu-south-2

Las empresas acogidas al SII deben enviar información de facturas a la AEAT en un plazo de 4 días hábiles. En despliegues sobre AWS eu-south-2 (región de Madrid), el enrutamiento de red hacia los servicios de la AEAT puede requerir un proxy de salida explícito para cumplir con las políticas de seguridad de red corporativas o restricciones del VPC.

Crea y Crece y plataformas de facturación B2B en redes corporativas

Con la entrada en vigor de la Ley Crea y Crece (B2B e-invoicing obligatorio previsto para 2027–2028, estándar EN 16931 / CIUS-ES), las plataformas de software de facturación que procesen y generen representaciones PDF de facturas B2B en redes corporativas deberán garantizar que IronPDF pueda acceder a los recursos HTML necesarios (plantillas, activos CSS, fuentes corporativas) a través del proxy. Se recomienda incluir los endpoints de las plataformas de recepción de facturas B2B y de validación Crea y Crece en la lista de exclusiones NO_PROXY para evitar latencias adicionales en el pipeline de facturación. La latencia desde AWS eu-south-2 hacia los servidores de la AEAT en Madrid es generalmente baja (< 5 ms), pero los proxies corporativos con inspección SSL pueden añadir 50-200 ms por petición — ajusta RenderingOptions.Timeout en consecuencia.

¿Cómo solucionar problemas de proxy?

Errores de tiempo de espera: Los proxies corporativos añaden latencia. Aumenta el tiempo de espera del render desde el valor predeterminado de 60 segundos:

renderer.RenderingOptions.Timeout = 120; // seconds
renderer.RenderingOptions.Timeout = 120; // seconds
renderer.RenderingOptions.Timeout = 120 ' seconds
$vbLabelText   $csharpLabel

Esta es la propiedad RenderTimeout — controla cuánto tiempo Chromium espera tanto para la carga de la página como para la obtención de recursos. Si tu proxy añade de 5 a 10 segundos de latencia por solicitud, y la página carga más de 20 recursos externos, 60 segundos pueden no ser suficientes.

Intercepción SSL (proxies MITM): Muchos proxies corporativos descifran y vuelven a cifrar el tráfico HTTPS utilizando un certificado raíz de CA corporativa. Chromium rechaza estas conexiones porque no confía en la CA corporativa por defecto. Dos soluciones:

  1. Instala el certificado de CA corporativa en el almacén de raíces confiables del contenedor o host. En Linux: copia el .crt a /usr/local/share/ca-certificates/ y ejecuta update-ca-certificates.
  2. Solo en desarrollo, puedes desactivar la validación de certificados — pero nunca lo hagas en producción. El enfoque más seguro siempre es instalar el certificado adecuado.

Autenticación NTLM: El formato user:pass@host en línea admite la autenticación de proxy Básica y de Digestión. NTLM (común en empresas centradas en Windows) no es compatible a través de la cadena URL del proxy. La solución es ejecutar un proxy local de reenvío NTLM-a-Basic como CNTLM en el host o como un contenedor sidecar. Configura CNTLM con tus credenciales NTLM, luego apunta IronPDF a http://localhost:3128 (el puerto predeterminado de CNTLM).

PDF en blanco o faltan recursos: Si el PDF se renderiza pero faltan imágenes/CSS, tu HTML hace referencia a recursos que el proxy bloquea o que requieren una ruta de proxy diferente. Verifica que el parámetro baseUrlOrPath se resuelva correctamente a través del proxy, y revisa los registros de acceso del proxy para respuestas 403 o 407.

Eludir proxy para recursos locales: Si tu HTML hace referencia a una mezcla de recursos locales (imágenes integradas, CSS en línea) y recursos remotos (fuentes CDN, scripts externos), el proxy solo necesita manejar las solicitudes remotas. Establece baseUrlOrPath en un directorio local para activos del sistema de archivos, y deja que el proxy maneje solo las solicitudes de red. Esto evita que las lecturas de archivos locales se enruten innecesariamente a través del proxy.

Diagnosticando la conectividad: Para verificar que tu cadena de proxy es correcta antes de usarla con IronPDF, pruébala primero con una solicitud simple HttpClient:

var proxy = new WebProxy("http://proxy.corp.local:8080");
var handler = new HttpClientHandler { Proxy = proxy, UseProxy = true };
using var client = new HttpClient(handler);

var response = await client.GetAsync("https://httpbin.org/ip");
Console.WriteLine(await response.Content.ReadAsStringAsync());
// Should return the proxy's external IP, not your machine's IP
var proxy = new WebProxy("http://proxy.corp.local:8080");
var handler = new HttpClientHandler { Proxy = proxy, UseProxy = true };
using var client = new HttpClient(handler);

var response = await client.GetAsync("https://httpbin.org/ip");
Console.WriteLine(await response.Content.ReadAsStringAsync());
// Should return the proxy's external IP, not your machine's IP
Imports System
Imports System.Net
Imports System.Net.Http

Dim proxy As New WebProxy("http://proxy.corp.local:8080")
Dim handler As New HttpClientHandler With {.Proxy = proxy, .UseProxy = True}
Using client As New HttpClient(handler)
    Dim response = Await client.GetAsync("https://httpbin.org/ip")
    Console.WriteLine(Await response.Content.ReadAsStringAsync())
    ' Should return the proxy's external IP, not your machine's IP
End Using
$vbLabelText   $csharpLabel

Si esto tiene éxito pero IronPDF aun así falla, el problema probablemente sea la interceptación SSL o un desajuste de protocolo entre tu proxy y el túnel CONNECT de Chromium. Verifica si el proxy soporta HTTP CONNECT para recursos HTTPS — algunos proxies requieren una configuración explícita para permitir el túnel.

Integración de proxy con la sede electrónica de la AEAT y servicios de facturación española

La configuración de proxy adquiere dimensiones normativas específicas cuando IronPDF accede a servicios de la AEAT o a las plataformas de las Haciendas Forales para verificar facturas o completar flujos de facturación electrónica.

Acceso a sede.agenciatributaria.gob.es desde red corporativa: Para aplicaciones que generan facturas VERI*FACTU y necesitan verificar el código QR de Factura verificable en la sede electrónica de la AEAT durante el proceso de generación, la configuración de proxy corporativo es esencial. El acceso a sede.agenciatributaria.gob.es desde entornos empresariales en España habitualmente requiere proxy con autenticación NTLM, especialmente en entidades financieras reguladas por el Banco de España o en grupos empresariales con infraestructura centralizada.

Proxies y portales Haciendas Forales (TicketBAI): Las aplicaciones que generan documentos TicketBAI para las tres Haciendas Forales del País Vasco — bizkaia.eus (BATUZ), gipuzkoa.eus y araba.eus — deben configurar el proxy corporativo para permitir el tráfico HTTPS hacia estos dominios. La configuración NO_PROXY debe excluir explícitamente los dominios forales y la AEAT para evitar que el proxy intercepte certificados SSL emitidos por la FNMT (Fábrica Nacional de Moneda y Timbre) usados en la firma PAdES conforme a eIDAS.

SII y FACe detrás de proxy: El SII (Suministro Inmediato de Información) de la AEAT expone servicios web REST para la remisión de libros de registro de IVA (Modelo 303 entre otros). El portal FACe de la Administración Pública española también opera tras HTTPS con certificados FNMT. Para aplicaciones desplegadas en AWS eu-south-2 (Madrid) que acceden a estos servicios, la configuración de proxy en el nivel Kubernetes (variables HTTP_PROXY/HTTPS_PROXY en el pod) evita la necesidad de cambiar el código de IronPDF en cada entorno.

LOPDGDD y logs de proxy: Los datos que transitan por el proxy durante el acceso a los servicios de la AEAT pueden incluir NIF/CIF de contribuyentes y datos de facturas sujetos a la LOPDGDD supervisada por la AEPD. Asegúrese de que los logs del proxy no persistan datos personales más allá del período de retención mínimo exigido, y que el proveedor del proxy haya firmado el acuerdo de tratamiento de datos correspondiente si actúa como encargado del tratamiento.

Crea y Crece y conectividad B2B: Con la entrada en vigor de la Ley Crea y Crece (B2B e-invoicing 2027–2028, estándar EN 16931/CIUS-ES), las plataformas de facturación necesitarán acceder a los puntos de acceso de la red de operadores de servicio. La configuración de proxy descrita en esta guía es el primer paso para garantizar que estos accesos funcionen correctamente en entornos empresariales con red perimetral estricta.

Próximos pasos

El soporte de proxy en IronPDF es un parámetro de método en RenderHtmlAsPdf() — pasa la cadena de proxy, y el motor Chromium enruta todo el tráfico HTTP a través de él. Para escenarios RenderUrlAsPdf(), obtén el HTML con HttpClient y un WebProxy primero. Para contenedores y CI/CD, las variables de entorno a nivel de sistema HTTPS_PROXY te dan control a nivel de infraestructura sin cambios de código.

Explora el cómo autenticarse y logins para autenticación en páginas web (distinta de la autenticación de proxy), la guía de encabezados de solicitud HTTP para encabezados personalizados, y la referencia de opciones de renderizado para ajustes de tiempo de espera y rendimiento.

Ver opciones de licencias a partir de $999. La referencia API ChromePdfRenderer documenta cada sobrecarga de método y la referencia ChromePdfRenderOptions cubre todas las propiedades configurables. RenderUrlAsPdf() ProxyAddress ChromePdfRenderOptions RenderHtmlAsPdf StaticRenderHtmlAsPdf RenderUrlAsPdf HttpClient WebProxy RenderHtmlAsPdf() ```yaml

spec: containers:

  • name: pdf-generator image: myregistry/pdf-service:latest env:

Preguntas Frecuentes

¿Cómo configuro un servidor proxy para la renderización de PDF en C#?

Para configurar un servidor proxy para la renderización de PDF en C#, puede usar el parámetro de proxy al llamar al método RenderHtmlAsPdf en IronPDF. Esto le permite especificar configuraciones de proxy para acceder a recursos web.

¿Cuál es el propósito de usar un proxy con IronPDF?

Usar un proxy con IronPDF ayuda a gestionar las solicitudes de red al renderizar PDFs, especialmente en entornos con acceso restringido a internet, como detrás de cortafuegos o en redes corporativas.

¿Puede IronPDF manejar proxies autenticados?

Sí, IronPDF puede manejar proxies autenticados. Debe proporcionar las credenciales de autenticación necesarias junto con las configuraciones de proxy en su código C#.

¿Es posible usar IronPDF con un proxy en un contenedor Docker?

Sí, IronPDF se puede configurar para trabajar con un proxy en un contenedor Docker. Asegúrese de que las variables de entorno de Docker estén configuradas correctamente para pasar las configuraciones de proxy.

¿Cómo resuelvo problemas de proxy con IronPDF?

Para resolver problemas de proxy con IronPDF, verifique sus configuraciones de proxy, asegúrese de que los detalles de autenticación sean correctos y verifique la accesibilidad de la red. Revisar cualquier mensaje de error en los registros también puede ayudar a identificar el problema.

¿Se puede usar IronPDF en pipelines de CI/CD con configuraciones de proxy?

Sí, IronPDF se puede integrar en pipelines de CI/CD con configuraciones de proxy. Asegúrese de que su entorno de compilación esté configurado para pasar las configuraciones de proxy necesarias durante el proceso de renderización de PDF.

¿Cuáles son los beneficios de usar un proxy con IronPDF en entornos empresariales?

Usar un proxy con IronPDF en entornos empresariales puede mejorar la seguridad, controlar el acceso a internet y gestionar el uso del ancho de banda, lo que facilita el cumplimiento de las políticas de TI de la organización.

Darrius Serrant
Ingeniero de Software Full Stack (WebOps)

Darrius Serrant tiene una licenciatura en Ciencias de la Computación de la Universidad de Miami y trabaja como Ingeniero de Marketing WebOps Full Stack en Iron Software. Atraído por la programación desde joven, vio la computación como algo misterioso y accesible, convirtiéndolo en el ...

Leer más
¿Listo para empezar?
Nuget Descargas 19,014,616 | Versión: 2026.5 just released
Still Scrolling Icon

¿Aún desplazándote?

¿Quieres una prueba rápida? PM > Install-Package IronPdf
ejecutar una muestra Mira cómo tu HTML se convierte en PDF.