Click here to Skip to main content
15,890,185 members
Please Sign up or sign in to vote.
1.00/5 (1 vote)
See more:
Hi,

I am writing following code in .NET Core Web API. And project is divided in "API", "Service", "Repository".
I have following request body and it is sending a mail with an attachment with a link given in "Attachment".

{
"To": "manoj.bisht@.....com",
"Cc": "",
"Bcc": "",
"Subject": "Test",
"Body": "This is test message",
"Attachment": "https://reports.contractorconnection.com/ReportsDisplay11.5/PDF_Report.aspx?param1=19444¶m2=NOMORE¶m3=¶m4=NOMORE¶m5=NOMORE¶m6=NOMORE¶m7=NOMORE¶m8=NOMORE¶m9=NOMORE¶m10=NOMORE¶m11=NOMORE¶m12=NOMORE¶m13=NOMORE¶m14=NOMORE¶m15=NOMORE&CRname=ContrApplication2012.rpt&CRcheck=NEEDED"
}

And it is working fine on my local system but as i am uploading on "Azure server" and running then it is giving an error of "Bad Request" and giving a
"Message": "Could not find file 'D:\\home\\site\\wwwroot\\PDF_Report.pdf'.",

And also i am not using 'D:\\home\\site\\wwwroot\\PDF_Report.pdf" in my code

What I have tried:

mail sending code is placed at Repository and it's creating a PDF File in "API" and after sending mail it is deleting file from "API"
I've tried in Repository

var result = 0;
            var client = new HttpClient();
            
            var fileUrl = objContractorOperationEmail.Attachment;
            bool pdfFileExtention = false;
            if (fileUrl.Contains(".aspx"))
            {
                pdfFileExtention = true;
            }

            var response = await client.GetAsync(fileUrl);

            string[] str = response.RequestMessage.RequestUri.LocalPath.Split('/');
            using (var stream = await response.Content.ReadAsStreamAsync())
            {
                if (pdfFileExtention == true)
                {
                    str[str.Length - 1] = str[str.Length - 1].Replace(".aspx", ".pdf");
                }

                var fileInfo = new FileInfo(str[str.Length - 1]);                
                using (var fileStream = fileInfo.OpenWrite())                
                {
                    await stream.CopyToAsync(fileStream);
                }
            }

            var attachments = str[str.Length - 1];
            objContractorOperationEmail.Attachment = attachments;

            bool isEmailSuccess = _mailRepository.SendContractorOperationEmail(objContractorOperationEmail);

            if (isEmailSuccess)
            {
                FileInfo file = new FileInfo(str[str.Length - 1]);
                if (file.Exists) //check file exsit or not if yes then delete the file
                {
                    file.Delete();
                }

                result = 1; //Success
            }

            return result;
Posted
Updated 17-Aug-21 23:01pm
Comments
Richard MacCutchan 18-Aug-21 3:31am    
Where does the error occur, and where is that message generated?
.NET- India 18-Aug-21 3:36am    
While i run this api on "localhost" then gets no error, but run on "Azure server swagger" then get following error......


400 Error: Bad Request
{
"ClassName": "System.Exception",
"Message": "Bad request found",
"Data": null,
"InnerException": {
"ClassName": "System.IO.FileNotFoundException",
"Message": "Could not find file 'D:\\home\\site\\wwwroot\\sample.pdf'.",
Richard MacCutchan 18-Aug-21 3:52am    
That is in your server code and it is definitely trying to reference an invalid path. Use your debugging tools to find out why; it is not something anyone here can do for you.
CHill60 18-Aug-21 4:03am    
I presume you have a D: drive mapped on your local system but the Azure server does not. Shouldn't you be using Server.MapPath to get the location of wwwroot for your site?
.NET- India 18-Aug-21 4:08am    
No, i have not used any "D:" in my local system.....

1 solution

Quote:
C#
string[] str = response.RequestMessage.RequestUri.LocalPath.Split('/');
// str contains: { ..., "PDF_Report.aspx" }

...

str[str.Length - 1] = str[str.Length - 1].Replace(".aspx", ".pdf");
// str contains: { ..., "PDF_Report.pdf" }

var fileInfo = new FileInfo(str[str.Length - 1]);
// fileInfo points to: "«CURRENT_DIRECTORY»\PDF_Report.pdf"
You are trying to write a file in the current working directory.

On Azure, that working directory is the root of your site: D:\home\site\wwwroot

The user your application is running as on Azure does not have permission to write to the root of the application. And it should not have that permission, since this would represent a potential security vulnerability.

Instead, you should be writing the file to the temporary folder:
C#
string tempFolder = Path.GetTempPath();
string filePath = Path.Combine(tempFolder, str[str.Length - 1]);
var fileInfo = new FileInfo(filePath);
But remember, your code could be accessed by multiple users at the same time. If you write the attachment to a file with a fixed name like PDF_Report, the file for one user could overwrite the file for another user. You could end up sending corrupted files as attachments. Or you could end up exposing private data belonging to one user to other users, which would mean you would face large fines.
 
Share this answer
 
v2

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900