2

I have an ASPMVC webapi application in which the client will attach an attachment. this attachment is the form byte[]. But on the server side we are not able to receive the attachment.

Here is the client code.

StringBuilder sbAPIRequest = new StringBuilder();
sbAPIRequest.Append("http://localhost:58229/api/SendEmailMessage");
sbAPIRequest.Append("&From=");
sbAPIRequest.Append(request.From);
sbAPIRequest.Append("&Subject=");
sbAPIRequest.Append(request.Subject);
sbAPIRequest.Append("&To=");
sbAPIRequest.Append(request.To);
sbAPIRequest.Append("&FileName=");
sbAPIRequest.Append(request.FileName);
sbAPIRequest.Append("&Body=");
sbAPIRequest.Append(request.Body);
sbAPIRequest.Append("&Data=");
sbAPIRequest.Append(System.IO.File.ReadAllBytes("File Path"));
HttpWebRequest httpWReq = (HttpWebRequest)WebRequest.Create(sbAPIRequest.ToString());
httpWReq.Method = "GET";
httpWReq.ContentType = "application/json;charset=UTF-8";
httpWReq.ContentLength = 0;
HttpWebResponse response = (HttpWebResponse)httpWReq.GetResponse();

Here is the service Side Code i.e. ASPMVC webapi

public IEnumerable<string> Get([FromUri] Models.EmailMessageRequest emailMessage)
        {
            MailMessage _MailMessage = new MailMessage();
            System.Net.Mail.Attachment attachment;
            List<string> Messages = new List<string>();    
            try
            {
                        UpdateMailAddressCollection(_MailMessage.Bcc, emailMessage.Bcc);
                        _MailMessage.Body = emailMessage.Body;
                        UpdateMailAddressCollection(_MailMessage.CC, emailMessage.CC);
                        _MailMessage.From = getMailAddress(emailMessage.From);
                        _MailMessage.IsBodyHtml = emailMessage.IsBodyHtml;
                        _MailMessage.Subject = emailMessage.Subject;
                        UpdateMailAddressCollection(_MailMessage.To, emailMessage.To);
                        _MailMessage.Priority = getPriority(emailMessage.Priority);

                        if (emailMessage.Data != null && emailMessage.Data[0] != 0)
                        {
                            Stream _Stream = new MemoryStream(emailMessage.Data);
                            attachment = new Attachment(_Stream, emailMessage.FileName);
                            _MailMessage.Attachments.Add(attachment);
                        }
                        string _smtp_host = (new S2.Services.Contracts.Schemas.Customer.AppSettingHelper()).smtp_host;
                        SmtpClient client = new SmtpClient(_smtp_host);
                        client.Send(_MailMessage);
                        response.Success = true;
                        response.Messages.Add("Email Sent successfully.");
            }
            catch (Exception ex)
            {
                response.Messages.Add("Internal Exception");
                response.Success = false;
            }

            Messages.Add(response.Messages.Select(x => x).FirstOrDefault() + " Success:" + response.Success);
            return Messages.ToList();
        }
Ajinkya Sawant
  • 100
  • 1
  • 13
  • Please also share some pice of code or work that you have done so far. – Ali Mar 04 '15 at 04:57
  • You cannot mix and match JSON data and file attachment. For posting a file, the content type should be "multipart/form-data" with a boundary. You can find some examples in http://www.asp.net/web-api/overview/advanced/sending-html-form-data,-part-2 and http://blogs.msdn.com/b/henrikn/archive/2012/03/01/file-upload-and-asp-net-web-api.aspx. One more similiar question http://stackoverflow.com/questions/10339877/asp-net-webapi-how-to-perform-a-multipart-post-with-file-upload-using-webapi-ht – Parthasarathy Mar 04 '15 at 05:42
  • @Sarathy i have added the following code in the client httpWReq.ContentType = "multipart/form-data"; but on the server side bytearray doest not contain data. – Ajinkya Sawant Mar 04 '15 at 06:02
  • Can you check the following link and modify your client code?http://stackoverflow.com/questions/566462/upload-files-with-httpwebrequest-multipart-form-data – Parthasarathy Mar 04 '15 at 06:16
  • @Sarathy i am sending bytearray from the client side and same bytearray need to come on the server side as service side datatype is byte array. From the client side it is sending the byte array but when it come to server side the bytearray it becomes 0 – Ajinkya Sawant Mar 04 '15 at 06:39
  • Can you post the updated code please? – Parthasarathy Mar 04 '15 at 07:11
  • Here is the client side code. The client application is windows application sbAPIRequest.Append("&Data="); sbAPIRequest.Append(request.Data); // This byte array data httpWReq.Method = "GET"; httpWReq.ContentType = "multipart/form-data"; httpWReq.ContentLength = 0; On Server side public IEnumerable Get([FromUri] Models.EmailMessageRequest emailMessage) {} the byte array in email message doest has the data. – Ajinkya Sawant Mar 04 '15 at 07:16

2 Answers2

2

To send an email with an attachment using a web api can be done in very simple manner.

In the services side i.e. an webapi code for sending an email with attachment is done as we do in C# using system.NET.Mail.

Here is the main trouble comes when client sending an attachment to webapi. if the client is using HttpWebRequest i.e sending the data using URL then there is one restriction the URL can carry up 2045 Byte of data. If a big size file is attachmented the it fails to carry the attachment.

The solution to the above is using HTTPClinet in the following manner in which you can send attachment of your required size where in you attachment get converted into JSON formate. Need to get HTTPClient from NUGETS.

  HttpClient client = new HttpClient();
                client.BaseAddress = new Uri("http://localhost:58229/");
                client.DefaultRequestHeaders.Clear();

                // Add an Accept header for JSON format.
                client.DefaultRequestHeaders.Accept.Add(
                    new MediaTypeWithQualityHeaderValue("application/json"));
                HttpRequestMessage Request = new HttpRequestMessage();
//You need to give the method name
                HttpResponseMessage _response = client.PostAsJsonAsync("api/SendEmail", request).Result;
Ajinkya Sawant
  • 100
  • 1
  • 13
0

You need to get file content as byte array the populate your mail object.

This link might help you

https://codesupport.wordpress.com/2014/05/22/webapi/

Sarmin Akter
  • 120
  • 7
  • if the client is windows application then how will you send byte array to mvc webapi application it which the attribute is [httpGet] and is send through URL – Ajinkya Sawant Mar 04 '15 at 06:53
  • Thanks ! @Ajinkya Sawant . It will get the InputStream of file from HttpRequest and then copy to the object of MemoryStream. Then put the MemoryStream object in a byte[] type variable by cast to array. The attatchment would be that byte[] type variable containing file content. – Sarmin Akter Mar 04 '15 at 10:13
  • yes your right what you said **"It will get the InputStream of file from HttpRequest"** it becomes empty when it reaches to server. – Ajinkya Sawant Mar 04 '15 at 10:22
  • @Ajinkya Sawant. can you please check that, it does exceed maximum content length or not. and have you tried like this- MemoryStream ms = new MemoryStream(); httpRequest.Files[0].InputStream.CopyTo(ms); byte[] attachment= ms.ToArray(); – Sarmin Akter Mar 04 '15 at 10:33