El archivo PDF no se carga en la aplicación asp.net

Tengo una aplicación ASP.NET que se ejecuta en:

Estándar de Windows Server 2019

IIS Versión 10.0.17763.1

La aplicación está configurada para usar HTTPS

La aplicación está utilizando la biblioteca System.Web.UI.WebControls.FileUpload para cargar archivos

La aplicación utiliza QuickPDFDLL0811.dll para leer archivos PDF y contar el número de páginas

Los usuarios han estado informando que ALGUNOS archivos PDF no se pueden cargar. La pestaña del navegador Chrome muestra una rueda giratoria como si la aplicación estuviera haciendo algo y luego a los usuarios se les presenta una página "No se puede acceder al sitio" (adjunta). Sin embargo, los mismos usuarios han indicado que han tomado los mismos archivos PDF que están dando error a través de los pasos que encontré en google aquí , y luego pueden cargar los archivos con éxito.

Además, tomé el mismo archivo que no se pudo cargar en producción y:

  1. Cargado en el servidor donde se ejecuta la aplicación PROD a través de HTTP y Chrome y tuvo éxito.
  2. Subido en nuestros entornos de prueba usando Chrome y vía HTTP y HTTPS y tuvo éxito.

No puedo compartir los archivos, ya que contienen datos confidenciales.

¿Alguien se ha encontrado con un problema similar? o alguien podría ofrecer alguna orientación? El hecho de que encontré una URL de la empresa docusign.com me indica que es un problema común.

EDITAR : estoy agregando el código que se ejecuta cuando se activa el problema (BtnUploadClick). Olvidé mencionar que también revisé los archivos de registro de IIS, pero no se registra nada con una respuesta fallida.

(Mis disculpas por el formato extraño, Stackoverflow lo estropea cuando copio/pego de VSCode)

protected void BtnUploadClick(object sender, EventArgs e)
{
try
{
    if (FileUpload.HasFiles)
    {
        
        foreach (var FileUpload in FileUpload.PostedFiles)
        {
            var uploadResult = Uploadfile(lstPrn, FileUpload);
            if (uploadResult.ReturnResponse == 
                             Enumerators.ResponseEnum.Success)
            {
                var objPrintFile = uploadResult.ReturnObject;
                lstPrn.Add(objPrintFile.FileName.ToUpper(), 
                           objPrintFile);
            }
        } 
    }
    else
    {
        lblFileCheck.Text = "You have not specified a file.";
        lblFileCheck.ForeColor = Color.Red;
    }
}
catch (Exception exception)
{
    //Log exception
}
}

private Response<PrintFile> Uploadfile(Hashtable lstPrn, 
HttpPostedFile FileUpload)
{
var result = new Response<PrintFile>();
var msg = "";
try
{
    if (Path.GetExtension(fileToWork).ToLower() == ".pdf")
    {
        PdfUtil myPdfUtil = new PdfUtil();

        objPrintFile.FileName = fileToWork;
        objPrintFile.ExpectedDocs = 
                myPdfUtil.GetNumberOfPdfPages(path + fileToWork);
        if (objPrintFile.ExpectedDocs > 0)
        {
            //Map object here
            try
            {
                Session.Add("NewRequestPrintFiles", lstPrn);

                result.ReturnResponse = 
                 Enumerators.ResponseEnum.Success;
                result.ReturnObject = objPrintFile;

                btnNextUpload.Enabled = true;
            }
            catch
            {
                //log message here
            }
        }
    }
}
catch (Exception ex)
{
    //Log error
}

return result;
}

public int GetNumberOfPdfPages(string fileName)
{
int totPages = 0;

if (!string.IsNullOrEmpty(fileName))
{
    using (StreamReader sr = new 
    StreamReader(File.OpenRead(fileName)))
    {
        Regex regex = new Regex(@"/Type\s*/Page[^s]");

        int bufSize = 10 * 1024;
        int lastPorSize = 20;
        char[] myBuffer = new char[bufSize + 1];
        char[] lastPortion = new char[lastPorSize];

        for (int c = 0; c < lastPorSize; c++)
            lastPortion[c] = '*';

        try
        {
            //read it by chunks!!
            while (!sr.EndOfStream)
            {
                int nBytes = sr.ReadBlock(myBuffer, 0, bufSize);
                string strToSerach = new string(lastPortion, 0, 
                lastPorSize) + new string(myBuffer, 0, nBytes);

                MatchCollection matches = 
                regex.Matches(strToSerach);
                foreach (Match match in matches)
                {
                    if (match.Index >= nBytes)
                    {
                        // I have to clean up if there is a match
                        // at the end of strToSerach because I 
                        //don't want that to be copied over
                        // lastPortion and count again on the 
                        //next iteration.
                        for (int c = 0; c < match.Length; c++)
                        {
                            if (match.Index + c > lastPorSize)
                                myBuffer[match.Index + c - 
                                lastPorSize] = '*';
                        }
                    }
                }

                for (int c = 0; c < lastPorSize; c++)
                {
                    if ((nBytes - lastPorSize + c) >= 0)
                    {
                        lastPortion[c] = myBuffer[nBytes - 
                                         lastPorSize + c];    
                    }
                }

                totPages += matches.Count;
            }
        }
        catch (Exception ex)
        {
            totPages = 0;
        }
    }
}
else
    totPages = 0;

return totPages;
}

EDITAR :

Adjunto una captura de pantalla de los archivos. El archivo 1 es igual que el archivo 2, pero observe que hay una diferencia de tamaño cuando el archivo 1 pasa por el proceso de "Imprimir en PDF" y luego se guarda localmente. El archivo 1 no se carga mientras que el archivo 2 se carga correctamente.

ingrese la descripción de la imagen aquí

ingrese la descripción de la imagen aquí

Answer

Su problema es sobre la experiencia, quiere que alguien que se haya encontrado con el mismo error le responda. Pero su problema necesita algunos detalles. Aunque intentaré responderte.

El escenario que describiste podría deberse a tres cosas...

  1. Al implementar algunas aplicaciones con editores o IDE como Visual Studio, notará que no se publican todas las carpetas o directorios. Algunos no están allí cuando implementa en producción o en su máquina. Entonces, la implicación de esto es que cuando finalmente implemente la aplicación, no contendría la carpeta a la que está tratando de cargar datos y si su código no contiene el bloque que verifica si el directorio existe o no y lo crea cuando no lo encuentra, el código falla. (Este proceso es publicando con Visual Studio IDE).

así que asegúrese de que su código verifique si el directorio existe; de ​​lo contrario, créelo.

  1. Cuando la configuración de seguridad del Directorio no permite escribir. Podría ser de solo lectura y no de lectura/escritura.

Se le pedirá que otorgue acceso de escritura a ese directorio en el que está tratando de cargar datos.

  1. Ruta absoluta para un recurso. A veces, en el código, la ruta a la carpeta en la que está escribiendo o cargando puede ser diferente en la producción.

Asegúrese de que la máquina de producción tenga la misma ruta para los recursos de implementación que su entorno de desarrollo.

NB: Los tres escenarios anteriores pueden hacer que el código funcione en una máquina de prueba pero no en producción porque si prueba en la máquina local, probablemente contendrá el directorio en el que está escribiendo o cargando. Y el acceso de lectura/escritura no necesita otorgarse en la máquina del desarrollador la mayoría de las veces, pero en producción, seguramente lo hará. Me sucedió cuando no pude verificar si el directorio existe o no y publiqué directamente desde mi IDE de Visual Studio en Microsoft Azure. Cuando intenté cargar imágenes, falló porque no se pudo encontrar el directorio. Aunque no apareció ningún mensaje de error.

Voy a aventurarme a adivinar que los archivos PDF que no se cargan tienen más de 4 MB. Si es así, lo que está encontrando es el límite de solicitud predeterminado de las aplicaciones asp.NET clásicas.

Consulte las respuestas a esta pregunta para saber cómo solucionarlo: ¿Cómo aumentar el tamaño máximo del archivo de carga en ASP.NET?

El comportamiento que ve, de "se restableció la conexión" se debe a que el servidor cierra la conexión cuando se alcanza el límite. Tiene que hacer esto, porque no puede enviar una respuesta hasta que la solicitud se haya recibido por completo, por lo que no tiene otra opción que terminar la conexión, lo que da como resultado el error que ve en el navegador. La razón por la que existe este límite es por razones de seguridad: un cliente malicioso podría abrumar los recursos de su servidor enviando solicitudes extremadamente grandes, extremadamente lentas. Por una razón similar, los servidores web también suelen requerir que los clientes transmitan datos a una velocidad razonable.

Aparentemente, en el núcleo de ASP.NET, el límite predeterminado de solicitudes aumentó a 30 MB, probablemente porque el límite de 4 MB es demasiado restrictivo en la web moderna.

Tuve que involucrar al equipo de redes ya que IIS ni siquiera registraba la solicitud. Mencionaron que habían aplicado algunas reglas de seguridad y nuestra aplicación se vio afectada. Después de hacer una excepción a las reglas que aplicaban, pudimos cargar con éxito los archivos que fallaban antes. No puedo decir exactamente qué tipo de reglas se aplicaron, ya que no trabajo con ese equipo, pero administran nuestro enrutamiento de tráfico y equilibrio de carga mediante una herramienta llamada "F5". Gracias chicos por su tiempo y orientación.