5

I have a page (somePage.aspx) and I need the content that has been generated as an Email body

<div id="DV_TimeReportWraper" runat="server" style="display:block">
    <table id="TBL_UsersinTblTime">
       <tr id="TR_UsersinTblTime">
         <td id="TD_H_Name" class="Dg">
             name                
         </td>
         <td id="TD_H_UserID" class="Dg">
             ID
         </td>
         <td id="TD_H_Status" class="Dg">
             initial Stage
         </td>
         <td id="TD_H_SignOutAutoExeState" class="Dg">
             current Stage
         </td>
       </tr>
       <%
           if(edata != null)
               for (int idx=0;idx<edata.Count;idx++) {
                   var row = edata[idx];
                   bool bgcl = (idx % 2) == 0;
                   string BgCol = "";
                   if (bgcl)
                       BgCol = "#70878F";
                   else
                       BgCol = "#E6E6B8";
       %>
       <tr style=" background-color:<%=BgCol%>">
           <td id="TD_Name">
               <% = row["name"] %>
            </td>
            <td id="TD_UserID">
                <%= row["UserId"]%>
            </td>
            <td id="TD_Status">
                <%
                    int uidForSrc = Convert.ToInt32(row["UserId"]);
                    string src = "images/SignedOutNoFrame.png";
                    if (UserDidnotSignOutTimeOut(uidForSrc))
                        src = "images/didnotSignOut.png";
                 %>
                 <input type="image" src="<% =src %>" style="width:25px" />
             </td>
             <td id="TD_SignOutAutoExeState" >
                 <% 
                     string EexcSrc = "";
                     string inputType ="hidden";
                     //this updates if needed then returns true= needed update false = isn't need
                     if (UpdatedTimeOutOKForUSER(uidForSrc))
                     {
                         inputType = "image";
                         excSrc = "/images/SignedOutNoFrame.png";
                     }
                 %>
                 <input type="<%=inputType %>" src="<%=EexcSrc %>" style="width:25px" />
             </td>
        </tr>
        <%
            if (idx == edata.Count - 1)
                sendLog();
            }
        %>
    </table>
</div>

code for sendLog()

public void sendLog()
{
    mail.aReciver="username@gmail.com";
    mail.bSubject="ttest";
    mail.cBody = DV_UsersInTblTime.InnerHtml;
    mail.HentalSend();
}

I can't get the value of content to assign mail.cBody with.
It's saying something about the value not being a literal etc'.

That is the method I'm using in an external class which works fine till this last attempt to add the functionality of page content as a body, how is it possible to achieve the result as needed here?

public static class mail
{
    public static string aReciver, bSubject, cBody;
    public static void HentalSend()
    {
        string SmtpServer = "smtp.gmail.com";
        int port = 587;
        string sender = "Sender@domain.com";
        string ReCiver = aReciver;
        string Subject = bSubject;
        string Body = cBody;
        string account = "mail@domain.com";
        string Pass = "123456";
        Send(SmtpServer, port, account, Pass, sender, Receiver, Subject, Body);
        ... //send() is another relevant method to this question, it does rest of mail settings
    }
}
Picrofo Software
  • 5,475
  • 3
  • 23
  • 37
LoneXcoder
  • 2,121
  • 6
  • 38
  • 76
  • 4
    This isn't answering your question but I noticed this hasn't been pointed out yet: your `mail` class is dangerous because it is declared static and has public static fields exposed. Static classes and static fields provide a global shared application state. Remember that webpages are multithreaded so if two people came across this code and both executed the `HentalSend` method at the same time, the email may contain data from the other user. To protect this, remove all `static` keywords from the mail class then simply call `mail m = new mail()` in `sendLog`. – Joshua Nov 04 '12 at 07:57
  • @Joshua you are very nice to subject this issue cause i was slowly moving to instanciate a class insted of declaring it `inrow style`, as i was beginning to learn, having both option open not really knowing the side effects,..said, ok ,if u know about raid (0not mirror) with hard drives ,"they say" that is not safe = don't use, i did, i put all my data on it, at 1'st i was backing up all of my data and since than i use it flawlessly for about 5 years . althogh your situation in my application is rear cause we are only 4 users (: though that's diffrent than raid example, this is try to avoid!! – LoneXcoder Nov 04 '12 at 20:30

5 Answers5

8

This code will get the generated HTML of your dynamic control in to a string variable.

StringBuilder stringBuilder = new StringBuilder();
StringWriter writer = new StringWriter(stringBuilder);
HtmlTextWriter htmlWriter = new HtmlTextWriter(writer);
try {
    DV_TimeReportWraper.RenderControl(htmlWriter);
} catch (HttpException generatedExceptionName) {
}

string DV_TimeReportWraper_innerHTML = stringBuilder.ToString();

Then just use DV_TimeReportWraper_innerHTML as the body of your email

You might have to create a loop in case this control has children controls. More on that here: http://msdn.microsoft.com/en-us/library/htwek607.aspx#Y472

boruchsiper
  • 2,016
  • 9
  • 29
  • 53
  • I think it would be less cumbersome to just hit the page with a WebClient request and let ASP.NET do what ASP.NET does and then just reap the benefits of the rendering engine. – Hardrada Nov 04 '12 at 06:32
  • Unless the page requeres authentication and/or stores parameters in a session variable. – boruchsiper Nov 04 '12 at 07:22
  • You can pass Credentials down on a WebClient request. See the Credentials property http://msdn.microsoft.com/en-us/library/system.net.webclient.credentials.aspx Session params can be sent via querystring if they are not delicate, in which case you can opt to send over SSL. – Hardrada Nov 04 '12 at 07:35
  • But then it wouldn't be "less cumbersome" than my approach. – boruchsiper Nov 04 '12 at 07:55
  • The only thing that would require "effort" would be using SSL for params. However, since the OP never stated such requirements are needed, I fail to see how invoking the rendering and not taking advantage of what ASP.NET does inherently is somehow more efficient and less prone to breaking, as well as code maint and sustainability. A single WebClient, even with creds added and a some variables on a url outweighs all that any day. – Hardrada Nov 04 '12 at 08:08
  • 1
    Oh yeah, one more thing... he needs the html of a particular control, not the entire page. – boruchsiper Nov 04 '12 at 09:13
  • Then you have a page with no markup but that ctrl. This not that hard to do. However, I am starting to detect "smells". There are getting things for "free" and doing things in such a way as to make that logic the focus of the task. I get the feeling that this is a page that already exists and that OP thinks he can use it for "DRY". I'm all about DRY, but there is a point where you just have to have a separate engine for something that can be used to generate reporting details. I suspect this to be the case. – Hardrada Nov 04 '12 at 14:26
  • @boruchsiper i am trying To Catch up with your discusion here , so first i want to thank you both , as i am having a real issue here . it would help me to solve a problem i have , i left it behind un done and moved to another porj, till i will be able to "fix" this , thanks for your targetted Answer , i will Test This ASAP ! – LoneXcoder Nov 04 '12 at 18:07
1

I'm making an assumption here that you are loading that page up and then trying to run the sendLog method after the page loads or during page load or otherwise during some part of the page life cycle. Trying to get the innerhtml of of something that isn't rendered yet wont' work.

Essentially, you need to render the page first, and then you get the contents.

[EDIT] I'm updating my answer to include how I would do this. Instead of writing the .NET code to force the render, as I stated in my comment above.. let ASP.NET do the dirty work for you.

    using(WebClient c=new WebClient()){
    var result=c.DownloadString(@"http://yourdomain.com/somePage.aspx/");
}

Now you can use the result from that call as the body of your email.

Hardrada
  • 728
  • 8
  • 19
  • thanks , but , did you 1 ) read first and second line in my Comments on that Post casue this site is not in english language: `taking to account that for example if lets say you could do it with a web cliant targetting the current page url , so*(I Do..) * must take care of the encoding problems ` + *2* what (assumming you're able to deal with (1) somehow and make an attribute for extraction with encoding, So 2 is what about hiding rest of page and showing only requested placeHolder , table or div in this case – LoneXcoder Nov 04 '12 at 17:44
  • sorry but i just read hidden part of rest of comments between you and mr `BoruchSiper` stating something about : `However, I am starting to detect "smells".There are ?? and doing things in such a way as to make that logic the focus of the task. <>??`, could you please "Transatle"(as i am not well spoken english) & i can understand what made you think somthing is wrong , i can't figure what or why , if i did, with this post , i'll be here to hear what ever it is – LoneXcoder Nov 04 '12 at 17:54
  • Well, first, can you explain if the page your trying to render is part of an existing website and if you're just trying to "re-use" that page because the code is already in that page? if Your answer is yes, then I would suggest that you create logic to build your output for both the page and the email in one contained unit of logic. My concern is that if your page rendering changes such that it won't work in an email, then you're left with making something specifically for email anyway. If you extracted this logic into something that created the html for the web and one for email = better way. – Hardrada Nov 04 '12 at 18:18
  • as a proggress i am on with(i'm learning with projcts i build), so every task i concuer is then stored in a namespace of collection of "helper method" +classes. so that's about the reuse. though this is not the case, its a 1'st time for me to try "grab" a specific content out-of a page, the page is a O.S schedualed task executed, activates a stored procedure which then returns value of table(before update) and results of action taken, thats a tipical plot of a the static _iest_ page you could ever ask for, so no posting back an forth, then self close with javascript suppressing alert – LoneXcoder Nov 04 '12 at 20:51
  • I guess I can re-word it like this. Does this page have an original purpose OTHER than generating HTML for the email? or is the ONLY purpose to generate HTML for the email? – Hardrada Nov 04 '12 at 23:52
  • Nop , as mentiond it only activates a stored procidure , it is first displaying current data from a table in Databse , then it shows table . stage before , stage after , renders that status html table , then closess the page via javascript suprressing "are you sure" .(request is , as this post subject :to add functionality of report to be logged* sent by email) report being that table or div – LoneXcoder Nov 05 '12 at 03:23
  • Then you are talking about just doing basic reporting. Have you thought about SSRS (SQL Server Reporting Services)? It was made for this type of stuff. – Hardrada Nov 05 '12 at 03:56
  • Thnks . i will look in to it ,if you can give me a good seacrch term to use google search on it will be fine ...like "using SSRS for ..." – LoneXcoder Nov 05 '12 at 15:13
  • here's some refs: http://blogs.msdn.com/b/brian_swan/archive/2010/04/29/getting-started-with-sql-server-reporting-services-ssrs.aspx http://msdn.microsoft.com/en-us/library/ms159106(v=sql.105).aspx http://www.youtube.com/watch?v=Cxv4-QNurCg just search for SSRS Tutorials. SSRS Means SQL Server Reporting Services. – Hardrada Nov 06 '12 at 03:51
  • If what you are simply trying to achieve is to log somewhere the fact that you just displayed a page. Just do it in the code behind of the page directly. You just accessed a database right ? Just call SendLog() right there after each access to DAL.GetInfo() or whatever. No need to try to pull stuff out of the html ..unless of course you basically want to send a sort screenshot of the page. – Robert Hoffmann Nov 09 '12 at 21:01
0

Try this ,

Add Namespaces

using System;
using System.Net.Mail;
using System.IO;
using System.Configuration;

Mail Function

public void SendHTMLMail()
{
StreamReader reader = new StreamReader(Server.MapPath("~/somePage.aspx"));
string readFile = reader.ReadToEnd();
string myString = "";
myString = readFile;
myString = myString.Replace("$$Admin$$", "Sajan SJ");
myString = myString.Replace("$$CompanyName$$", "RFT");
myString = myString.Replace("$$Email$$", "sajan@roomfortekki.com");
myString = myString.Replace("$$Website$$", "http://www.roomfortekki.com");
MailMessage Msg = new MailMessage();
MailAddress fromMail = new MailAddress("sajan@roomfortekki.com");
// Sender e-mail address.
Msg.From = fromMail;
// Recipient e-mail address.
Msg.To.Add(new MailAddress("sajan@roomfortekki.com"));
// Subject of e-mail
Msg.Subject = "Send Mail with HTML File";
Msg.Body = myString.ToString();
Msg.IsBodyHtml = true;
string sSmtpServer = "";
sSmtpServer = "10.2.69.121";
SmtpClient a = new SmtpClient();
a.Host = sSmtpServer;
a.Send(Msg);
reader.Dispose();
}
sajanyamaha
  • 3,119
  • 2
  • 26
  • 44
0

Hardrada is pointing in the right direction here

On your server underneath the .ASPX file, add the required localization files

\App_LocalResources
    somePage.aspx.en.resx
    somePage.aspx.es.resx
    somePage.aspx.fr.resx
somePage.aspx
  • Add your translations
  • Insert them in your aspx file

Call your file as suggested, except with a querystring

/somePage.aspx?culture=fr

And inside somepage.aspx, in the OnLoad() or OnInit() set:

var culture = System.Globalization.CultureInfo.CreateSpecificCulture(Request["culture"])

if (culture != null)
   System.Threading.Thread.CurrentThread.CurrentUICulture = culture;

Voila!

Robert Hoffmann
  • 2,366
  • 19
  • 29
0

SendEmail Button Click Code:

    protected void BtnSendIngMail_Click(object sender, EventArgs e)
    {

       StringBuilder stringBuilder = new StringBuilder();
        StringWriter writer = new StringWriter(stringBuilder);
        HtmlTextWriter htmlWriter = new HtmlTextWriter(writer);
        try
        {

            DivSendMail.RenderControl(htmlWriter);
        }
        catch (HttpException generatedExceptionName)
        {
            e.ToString();
        }

        try
        {

            string DefProductTemp_Html = stringBuilder.ToString();

            //send mail
            string smtpServer = Convert.ToString(DotNetNuke.Common.Globals.HostSettings["SMTPServer"]);
            string uid = Convert.ToString(DotNetNuke.Common.Globals.HostSettings["SMTPUsername"]);
            string upwd = Convert.ToString(DotNetNuke.Common.Globals.HostSettings["SMTPPassword"]);

          //  DotNetNuke.Services.Mail.Mail.SendMail(uid, txtMail.Text, uid, "Proforma Invoice", DefProductTemp_Html, "", DotNetNuke.Services.Mail.MailFormat.Html.ToString(), "", "", "", "");

            System.Net.Mail.MailMessage mail = new System.Net.Mail.MailMessage();
            System.Net.Mail.SmtpClient client = new SmtpClient();
            mail.To.Add(txtMail.Text);
            mail.From = new System.Net.Mail.MailAddress(uid);
            mail.Subject = ddlSubList.SelectedItem.Text;
            mail.SubjectEncoding = System.Text.Encoding.UTF8;
            mail.IsBodyHtml = true;


            mail.Body = DefProductTemp_Html;

            //mail.BodyEncoding = System.Text.Encoding.UTF8;

            //mail.Priority = System.Net.Mail.MailPriority.High;
            client.Credentials = new System.Net.NetworkCredential(uid, upwd);

            //client.Host = "localhost";
            client.Host = "smtp.gmail.com";
            client.Port = 587;
            client.EnableSsl = true;
            client.Send(mail);
        }
        catch (Exception ex)
        {
           // catch
        }
winner_joiner
  • 12,173
  • 4
  • 36
  • 61
shweta
  • 1
  • 1