Delete attached files after sending mail via SmtpClient ( ASP.NET MVC) - c#

I'm working on a website that can send a form with multiple files attached/upload, the files that are being attached is stored in the App_Data/uploads folder. Is there a chance that the file in the App_Data/uploads folder will be deleted right after it's send in the email? Thank you for your help. This is my controller:
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<ActionResult> Index(EmailFormModel model, IEnumerable<HttpPostedFileBase> files)
{
if (ModelState.IsValid)
{
List<string> paths = new List<string>();
foreach (var file in files)
{
if (file.ContentLength > 0)
{
var fileName = Path.GetFileName(file.FileName);
var path = Path.Combine(Server.MapPath("~/App_Data/uploads"), fileName);
file.SaveAs(path);
paths.Add(path);
}
}
var message = new MailMessage();
foreach (var path in paths)
{
var fileInfo = new FileInfo(path);
var memoryStream = new MemoryStream();
using (var stream = fileInfo.OpenRead())
{
stream.CopyTo(memoryStream);
}
memoryStream.Position = 0;
string fileName = fileInfo.Name;
message.Attachments.Add(new Attachment(memoryStream, fileName));
}
//Rest of business logic here
string EncodedResponse = Request.Form["g-Recaptcha-Response"];
bool IsCaptchaValid = (ReCaptcha.Validate(EncodedResponse) == "True" ? true : false);
if (IsCaptchaValid)
{
var body = "<p><b>Email From:</b> {0} ({1})</p><p><b>Subject:</b> {2} </p><p><b>Message:</b></p><p>{3}</p><p><b>Software Description:</b></p><p>{4}</p>";
message.To.Add(new MailAddress("***#gmail.com"));
message.From = new MailAddress("***#ymailcom");
message.Subject = "Your email subject";
message.Body = string.Format(body, model.FromName, model.FromEmail, model.FromSubject, model.Message, model.Desc);
message.IsBodyHtml = true;
using (var smtp = new SmtpClient())
{
var credential = new NetworkCredential
{
UserName = "***#gmail.com",
Password = "***"
};
smtp.Credentials = credential;
smtp.Host = "smtp.gmail.com";
smtp.Port = 587;
smtp.EnableSsl = true;
await smtp.SendMailAsync(message);
ViewBag.Message = "Your message has been sent!";
ModelState.Clear();
return View("Index");
}
} else
{
TempData["recaptcha"] = "Please verify that you are not a robot!";
}
} return View(model);
}

You can use SmtpClient's SendCompleted event to delete the file after sending:
smtp.SendCompleted += (s, e) => {
//delete attached files
foreach (var path in paths)
System.IO.File.Delete(path);
};
so the sending part should look like this:
using (var smtp = new SmtpClient())
{
var credential = new NetworkCredential
{
UserName = "***#gmail.com",
Password = "***"
};
smtp.Credentials = credential;
smtp.Host = "smtp.gmail.com";
smtp.Port = 587;
smtp.EnableSsl = true;
smtp.SendCompleted += (s, e) => {
//delete attached files
foreach (var path in paths)
System.IO.File.Delete(path);
};
await smtp.SendMailAsync(message);
ViewBag.Message = "Your message has been sent!";
ModelState.Clear();
return View("Index");
}

Related

SMTP Email and ERR_CONNECTION_RESET Error in Angular Project

Hi when i use the below code in angular api project my requests are not getting saved and i am gettign this following error. And when i comment the code to send mail everything is working fine
ERROR in console
polyfills POST net::ERR_CONNECTION_RESET
And code to send mail
public async Task SendEmail(string email, string subject, string firstName, string contact)
{
try
{
string message = BuildMessageBody(firstName, email, contact);
using (var client = new SmtpClient())
{
var networkCredential = new NetworkCredential
{
UserName = _configuration["Email:Email"],
Password = _configuration["Email:Password"]
};
client.UseDefaultCredentials = false;
client.Credentials = networkCredential;
client.Host = _configuration["Email:Host"];
client.Port = int.Parse(_configuration["Email:Port"]);
client.EnableSsl = true;
using (var emailMessage = new MailMessage())
{
emailMessage.To.Add(new MailAddress(email));
emailMessage.CC.Add(new MailAddress("my cc adddress"));
emailMessage.From = new MailAddress(_configuration["Email:Email"]);
emailMessage.Subject = subject;
emailMessage.Body = message;
emailMessage.IsBodyHtml = true;
emailMessage.BodyEncoding = System.Text.Encoding.UTF8;
emailMessage.SubjectEncoding = System.Text.Encoding.Default;
emailMessage.ReplyToList.Add(new MailAddress(_configuration["Email:Email"]));
client.SendCompleted += (s, e) => {
client.Dispose();
emailMessage.Dispose();
};
await client.SendMailAsync(emailMessage);
}
}
await Task.CompletedTask;
}
catch (Exception ex)
{
_appLogger.CreateLog("SendEmail - " + ex.Message);
}
}
Any idea why this behaviour???

How to delete the uploaded files in the "/App_Data/uploads" folder ASP.NET MVC

I can upload/attach files when I'm sending message in email. The files are being stored in the App_Data/uploads folder, so when I'm trying to send multiple files it takes long time before I can send it. I think it's because the folder already have many files, so I want to delete the files in folder when it's already send in email. Please help me. I'm just new with this kind of stuff. Thank you! Here's the controller:
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<ActionResult> Index(EmailFormModel model, IEnumerable<HttpPostedFileBase> files)
{
if (ModelState.IsValid)
{
List<string> paths = new List<string>();
foreach (var file in files)
{
if (file.ContentLength > 0)
{
var fileName = Path.GetFileName(file.FileName);
var path = Path.Combine(Server.MapPath("~/App_Data/uploads"), fileName);
file.SaveAs(path);
paths.Add(path);
}
}
var message = new MailMessage();
foreach (var path in paths)
{
var fileInfo = new FileInfo(path);
var memoryStream = new MemoryStream();
using (var stream = fileInfo.OpenRead())
{
stream.CopyTo(memoryStream);
}
memoryStream.Position = 0;
string fileName = fileInfo.Name;
message.Attachments.Add(new Attachment(memoryStream, fileName));
}
//Rest of business logic here
string EncodedResponse = Request.Form["g-Recaptcha-Response"];
bool IsCaptchaValid = (ReCaptcha.Validate(EncodedResponse) == "True" ? true : false);
if (IsCaptchaValid)
{
var body = "<p>Email From: {0} ({1})</p><p>Subject: {2} </p><p>Message:</p><p>{3}</p>";
message.To.Add(new MailAddress("***#gmail.com")); // replace with valid value
message.From = new MailAddress("***#ymailcom"); // replace with valid value
message.Subject = "Your email subject";
message.Body = string.Format(body, model.FromName, model.FromEmail, model.FromSubject, model.Message);
message.IsBodyHtml = true;
using (var smtp = new SmtpClient())
{
var credential = new NetworkCredential
{
UserName = "***#gmail.com", // replace with valid value
Password = "***" // replace with valid value
};
smtp.Credentials = credential;
smtp.Host = "smtp.gmail.com";
smtp.Port = 587;
smtp.EnableSsl = true;
await smtp.SendMailAsync(message);
//return RedirectToAction("Sent");
ViewBag.Message = "Your message has been sent!";
//TempData["message"] = "Message sent";
ModelState.Clear();
return View("Index");
}
}
else
{
TempData["recaptcha"] = "Please verify that you are not a robot!";
}
}
return View(model);
}
intially check for file existence then try below code
File.Delete("~/App_Data/uploads/XXXXX.xls");
Before to send on email you have to check first ...
if (System.IO.File.Exists(fullPath of your file))
{
System.IO.File.Delete(fullPath of your file);
}
try this:
System.IO.DirectoryInfo di = new DirectoryInfo(path);
foreach (FileInfo file in di.GetFiles())
{
file.Delete();
}
I strongly recommend to not use App_Data folder for storing any files , by convention is created only for storing database files.

Why My multiple email sending system is not working?

I am trying to send Email who are listed in my Userprofiles table and i have also added 2 columns like PhoneNo and Email. And also added values in this table. My wish is to send email these listed persons at a time. Now it is sending only one mail at a time. I have tried this code but it is not working. Please Help..
public ActionResult SendEmail(string address, string subject, string message)
{
if (ModelState.IsValid)
{
var v = (from e in db.todaySalesReport()
select e).SingleOrDefault();
var ctx = new UsersContext();
string from = "";
foreach (var i in ctx.UserProfiles.ToList())
{
address = i.Email;
//MailAddress addr = new MailAddress();
using (MailMessage mail = new MailMessage(from, address))
{
mail.To.Add(i.Email);
mail.Subject = "Total Sales Report for today";
mail.Body = "Total sales" + v.qty.ToString() + "Peices.";
mail.IsBodyHtml = false;
SmtpClient smtp = new SmtpClient();
smtp.Host = "smtp.gmail.com";
smtp.EnableSsl = true;
NetworkCredential networkCredential = new NetworkCredential(from, "");
smtp.UseDefaultCredentials = false;
smtp.Credentials = networkCredential;
smtp.Port = 587;
smtp.Send(mail);
ViewBag.Message = "Sent";
return View("Index", address);
}
}
}
else
{
return View();
}
return RedirectToAction("Index");
}
This is because you are returning your view inside your foreach loop. Take this code out of the foreach loop:
return View("Index", address);
It should be like this:
if (ModelState.IsValid)
{
var v = (from e in db.todaySalesReport()
select e).SingleOrDefault();
var ctx = new UsersContext();
string from = "";
foreach (var i in ctx.UserProfiles.ToList())
{
address = i.Email;
//MailAddress addr = new MailAddress();
using (MailMessage mail = new MailMessage(from, address))
{
mail.To.Add(i.Email);
mail.Subject = "Total Sales Report for today";
mail.Body = "Total sales" + v.qty.ToString() + "Peices.";
mail.IsBodyHtml = false;
SmtpClient smtp = new SmtpClient();
smtp.Host = "smtp.gmail.com";
smtp.EnableSsl = true;
NetworkCredential networkCredential = new NetworkCredential(from, "");
smtp.UseDefaultCredentials = false;
smtp.Credentials = networkCredential;
smtp.Port = 587;
smtp.Send(mail);
ViewBag.Message = "Sent";
}
}
return View("Index", address);
}
You have this
return View("Index", address);
dangling at the end of your loop. Move it out of the loop and it should be fine.

Search for files in a directory find them and email them

In a part of my program the application should search for certain files in installation directory and, if found, should email those files. So far I have:
try
{
MailMessage mail = new MailMessage();
string[] file1 = Directory.GetFiles("some directories", "some files");
string[] file2 = Directory.GetFiles("some directories", "some files");
string[] file3 = Directory.GetFiles("some directories", "some files");
foreach (var file in file1)
{
Attachment someFiles = new Attachment(file);
mail.Attachments.Add(someFiles);
}
foreach (var file in file2)
{
Attachment someFiles1 = new Attachment(file);
mail.Attachments.Add(someFiles1);
}
foreach (var file in file3)
{
Attachment someFiles2 = new Attachment(file);
mail.Attachments.Add(someFiles2);
}
SmtpClient server = new SmtpClient("smtp.gmail.com");
mail.From = new MailAddress("someone#gmail.com");
mail.To.Add("someone#gmail.com");
mail.Subject = "subject";
server.Port = 587;
server.Credentials = new System.Net.NetworkCredential("someone#gmail.com", "password");
server.EnableSsl = true;
server.Send(mail);
}
catch (Exception ex)
{
string stat = ex.ToString();
MessageBox. Show(stat);
}
There is no exception but no email is sent. Where is the problem?

How to send email with attachment of file without extension?

I created C# Console App and I can't send email with file attachment named "testfile" and has no extension.
It successfully sends, but with only the first attachment ("test.png")
How can I send this file?
Here is my code:
internal static void SendTest()
{
MailMessage mail = new MailMessage("Punter#gmail.com", "Michael378#live.com",
"Success", "Attachment email");
SmtpClient SmtpServer = new SmtpClient("smtp.gmail.com", 587);
SmtpServer.Credentials = new System.Net.NetworkCredential("Punter#gmail.com", "BrudoTass");
SmtpServer.EnableSsl = true;
string test1 = #"C:\Users\Admin\Desktop\test.png"; //Picture
string test2 = #"C:\Users\Admin\Desktop\testfile"; //File without extension
var attachment1 = new Attachment(test1);
var attachment2 = new Attachment(test2);
mail.Attachments.Add(attachment1);
mail.Attachments.Add(attachment2);
SmtpServer.Send(mail);
}
Try This way
foreach (MessageAttachment ma in msg.Attachments)
mail.Attachments.Add(BuildAttachment(ma));
private Attachment BuildAttachment(MessageAttachment ma)
{
Attachment att = null;
if (ma == null || ma.FileContent == null)
return att;
att = new Attachment(new MemoryStream(ma.FileContent), ma.FileName + ma.FileType, ma.FileType.GetMimeType());
att.ContentDisposition.CreationDate = ma.CreationDate;
att.ContentDisposition.ModificationDate = ma.ModificationDate;
att.ContentDisposition.ReadDate = ma.ReadDate;
att.ContentDisposition.FileName = ma.FileName;
att.ContentDisposition.Size = ma.FileSize;
return att;
}

Categories