尝试将生成的 pdf 文件上传到 Azure Blob 存储时出现 404 错误

Posted

技术标签:

【中文标题】尝试将生成的 pdf 文件上传到 Azure Blob 存储时出现 404 错误【英文标题】:404 Error when trying to upload a generated pdf file to Azure Blob Storage 【发布时间】:2021-10-15 20:06:07 【问题描述】:

这是我得到的错误:Microsoft.WindowsAzure.Storage.StorageException: '远程服务器返回错误:(404) Not Found.

关于以下代码:

使用 PDFSharp 生成 PDF 的第一种方法:

[Route("cpd-services/generate-generic-sla/cpd_services_id/userid")]
    public ActionResult GenerateGenericClientSLA(int cpd_services_id, int userId)
    
        var genericSLA = m_cpdServicesRepository.GetCPDServicesGenericSubscriptionDetail(cpd_services_id, userId);

        string SLAContent = m_cpdServicesRepository.GetSLATemplateByType(CPDServicesSLAHelpers.GenericClientDraftSLA);

        SLAContent = InsertGenericSLAData(SLAContent, genericSLA);

        var SLATitle = "GenericSLA" + "-" + userId;

        PdfDocument document = PdfGenerator.GeneratePdf(SLAContent, PdfSharp.PageSize.A4);
        PdfGenerateConfig config = new PdfGenerateConfig();
        config.PageSize = PdfSharp.PageSize.A4;
        var file = File(PDF.PDFDocumentToBytes(document), "application/pdf");
        file.FileDownloadName = SLATitle.ToLower() + ".pdf";

        return UploadGenericSLA(file, userId, cpd_services_id, SLATitle);
    

UploadGenericSLA 方法:

public JsonResult UploadGenericSLA(FileContentResult file, int userId, int CPDServicesId, string sla)
    
        Storage storage = new Storage(Settings);

        string filename = storage.UploadPDFDocument(file, "documents/cpd-services-service-level-agreement/generic/cpd-" + CPDServicesId + "/" + sla.Trim().ToLower() + ".?");

        int result = m_cpdServicesRepository.AddCPDServicesGenericSLA(file.FileDownloadName.Trim().ToLower(), CPDServicesSLAHelpers.GenericClientDraftSLA, userId, CPDServicesId);

        if (result > 0)
        
            TempData[CRUDResult.CRUDMessage] = $"CRUDResult.Success|SLA has been successfully generated";
            new TelemetryHelper  .TrackTrace($"SLA Generation - CPDServicesId", Microsoft.ApplicationInsights.DataContracts.SeverityLevel.Information);
            return Json(result);
        
        else
        
            TempData[CRUDResult.CRUDMessage] = $"CRUDResult.Failed|SLA Generation Failed";
            return Json(result);
        
    

这又会在我的 Storage.cs 类上触发此方法:

public string UploadPDFDocument(FileContentResult file, string filename)
    
        return UploadPDFFile($"Settings.StoragePath/Settings.Environment", file, filename);
    

protected string UploadPDFFile(string container, FileContentResult file, string filename)
    
        CloudStorageAccount storageAccount = CloudStorageAccount.Parse(Settings.AzureStorageConnectionString);
        CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
        CloudBlobContainer blobContainer = blobClient.GetContainerReference(container.ToLower());


        if (filename.EndsWith(".?"))
        
            int pos = file.FileDownloadName.LastIndexOf(".");
            filename = (filename.Substring(0, filename.Length - 1) + file.FileDownloadName.Substring(pos + 1)).ToLower();
        

        CloudBlockBlob blob = blobContainer.GetBlockBlobReference(filename.ToLower());

        blob.Properties.ContentType = "application/pdf";

        blob.SetProperties(); //This is where the request to the blob storage fails.

        blob.Metadata.Add("ContentType", "application/pdf");
        blob.Metadata.Add("Size", file.FileContents.Length.ToString());
        blob.Metadata.Add("ContentLength", file.FileContents.Length.ToString());
        blob.Metadata.Add("Filename", filename);

        if (FileExists(container, filename))
        
            blob.CreateSnapshot();
        

        blob.UploadFromByteArray(file.FileContents, 0, file.FileContents.Length);

        return filename;
    

这是 FileExists 方法的代码:

protected bool FileExists(string container, string filename)
    
        CloudStorageAccount storageAccount = CloudStorageAccount.Parse(Settings.AzureStorageConnectionString);
        CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
        CloudBlobContainer blobContainer = blobClient.GetContainerReference(container);

        CloudBlockBlob blob = blobContainer.GetBlockBlobReference(filename);

        return blob.Exists();
    

我们目前使用的是 WindowsAzure.Storage - 公司还不想升级...

任何帮助将不胜感激

【问题讨论】:

您在代码中的哪个位置收到此错误?请同时包含 FileExists 方法的代码。 @GauravMantri 所以我添加了 FileExists 方法的代码,我在 blob.SetProperties(); 旁边添加了注释这是我得到 404 错误的地方 如果我取出 blob.properties.ContentType,我的文件将保存一个八位字节/流而不是 application/pdf 请在此处查看我的答案:***.com/questions/24621664/…。 @GauravMantri 谢谢你,先生,我一定会试一试 【参考方案1】:

你可以排除 blob.SetProperties() 方法。

尝试一下,如果不起作用,请尝试为内容类型设置 Blobhttpheaders。 请参阅this 线程以获取@Gaurav Mantri 建议的可能解决方案。

还可以尝试将属性拆分为两个步骤 (reference)

BlobProperties blobProperties = blockblob.Properties;

blobProperties.ContentType = "应用程序/pdf";

Other reference

【讨论】:

以上是关于尝试将生成的 pdf 文件上传到 Azure Blob 存储时出现 404 错误的主要内容,如果未能解决你的问题,请参考以下文章

将 PDF ( > 4 MB) 上传到 D365 CRM 中的文件数据类型

使用 UploadFromFile 将文件上传到 Azure

将文件上传到 Azure Blob 存储时没有触发事件网格事件——为啥?

如何将文件上传到 c# Azure Function 生成的 FTP/webdav? [复制]

使用 rest api 从 Web 应用程序将文件上传到 Azure 文件存储

尝试通过节点 js 将 zip 文件上传到 azure 存储