HTML code in a specific format - python

I have the HTMl code #http://pastie.org/8456333 as a reference ,also I have the below code where i am construcing HTML code to email ..i need inputs or suggestions on what modifcations need to be done to below code to make the table look like
the HTML code #http://pastie.org/8456333
import re
import os
import sys
import time
from email.mime.text import MIMEText
import subprocess
from subprocess import check_call,Popen,PIPE
def email (body,subject,to=None):
msg = MIMEText("%s" % body)
msg["Content-Type"] = "text/html"
msg["From"] = "cdit#company.com"
#msg["From"] = "test#company.com"
if to!=None:
to=to.strip()
#msg["To"] = "test#company.com"
msg["To"] = to
else:
msg["To"] = to
msg["Subject"] = '%s' % subject
p = Popen(["/usr/sbin/sendmail", "-t"], stdin=PIPE)
p.communicate(msg.as_string())
def manifest_table(project,branch):
global table_items
global tableProperties
table_items = table_items + "<tr><td>%s</td><td>%s</td></tr>"%(project,branch)
tableBody = """\
<style type="text/css">
%s
</style>
<table id="tfhover" class="tftable" border="1">
%s
</table>
"""%(tableProperties, table_items)
return tableBody
def main ():
i=0
global table_items
table_items = "<tr><th>Project</th><th>Branch</th></tr>"
global tableProperties
tableProperties = r"table.tftable {font-size:12px;color:#333333;width:10%;border-width: 1px;border-color: #729ea5;border-collapse: collapse;} table.tftable th {font-size:12px;background-color:#ded0b0;border-width: 1px;padding: 8px;border-style: solid;border-color: #729ea5;text-align:left;} table.tftable tr {background-color:#ffffff;} table.tftable td {font-size:12px;border-width: 1px;padding: 8px;border-style: solid;border-color: #729ea5;}"
project_list=['data','modem','1x','umts']
branch_list=['jb','fr','kk','choc']
for proj in project_list:
branch = branch_list[i]
mft = manifest_table(proj,branch)
i=i+1
email_body = """\
<html>
<head></head>
<body>
<p>Please find the table for the gerrits you provided:- <br>
</p>
%s
</body>
</html>
"""%(mft)
print "Emailing..."
email(email_body,"Manifest table","test#company.com")
if __name__ == '__main__':
main()

For making your table I suggest to use string.Template:
this is simple example:
from string import Template
a = Template("$name is my friend")
b=a.substitute(name="Sara")
print b
#output: Sara is my friend
So about a part of your code:
table_items = table_items + "<tr><td>%s</td><td>%s</td></tr>"%(project,branch)
you can do it better:
table_items += "<tr><td>%(p)s</td><td>%(b)s</td></tr>" % {'p':project,'b':branch}
or via string.Template:
table_items = Template("<tr><td>$p</td><td>$b</td></tr>")
table_items += table_items.substitute(p=project,b=branch)

Related

Attempting to write multiple pandas dataframes to an email and send it

I was able to create two dataframe lists and translate them into HTML, but I would like to know how to include them in order so they will populate my email I intend to send each day. I have updated my code and question on this post. For each {0), {1}, etc I would like to insert a dataframe. Is that possible?
import datetime
import smtplib
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.mime.image import MIMEImage
import pandas as pd
import matplotlib
ALL_DFS = [L_MUNIC_s, L_MUNIF_s, L_CAMNY_s, L_NYMNY_s]
ALL_DFS_html= ''
for ALL_DF in ALL_DFS:
ALL_DFS_html += ALL_DF.render()
ALL_DFS2 = [L_MUNIC_NAV, L_MUNIF_NAV, L_MUNIC5, L_MUNIF5]
ALL_DFS_html2= ''
for ALL_DF2 in ALL_DFS2:
ALL_DFS_html2 += ALL_DF2.to_html()
def send_mail():
dataf1 = ALL_DF
dataf2 = ALL_DF2
sender = "<name>#gmail.com"
receiver = ['<name>#gmail.com']
msg = MIMEMultipart('related')
today = datetime.date.today()
msg['Subject'] = "Daily Email " +
str(today.strftime("%m/%d/%y"))
msg['From'] = sender
msg['To'] = ", ".join(receiver)
html = """\
<html>
<head></head>
<body>
<p>Good Morning Team!<br>
L-MUC
NET ASK: {0}
Exposure:<br>
{1}
<br>Top 5:<br>
{2}
<br>
<br>NEW:<br>
{3}
<br>
</p>
<p>
L-MUF
NET ASK: {4}
Exposure:<br>
{5}
<br>Top 5:<br>
{6}
<br>
<br>NEW:<br>
{7}
<br>
</p>
<p>
L-CAY
NEW ASK: {8}
Exposure:<br>
{9}
<br>NEW:<br>
{10}
<br>
</p>
<p>
L-NYY
NEW ASK: {11}
Exposure:<br>
{12}
<br>NEW:<br>
{13}
<br>
</p>
</body>
</html>
""".format(dataf1.render(), dataf2.to_html())
partHTML = MIMEText(html, 'html')
msg.attach(partHTML)
ser = smtplib.SMTP('gateway_server', port_number)
ser.login("username", "password")
ser.sendmail(sender, receiver, msg.as_string())
return send_mail()
If the link provided in the comments doesn't answer your question, I wonder if this could solve your problems.
# Let's assume you have some list of dataframes.
dfs = [pd.DataFrame({'col1': [1, 2], 'col2': [3, 4]}) for _ in range(4)]
dfs_html = ''
for df in dfs:
dfs_html += df.to_html()
dfs_html is now a nicely formatted bit of html with all your data.

how to break line in list in python email

I am trying to query a list from my Flask database and then send it out as a html email. However, i am unable to break them into different lines.
for example, instead of:
a
b
c
i get abc currently in the email. i've tried adding "\n" in the loop but it doesnt seem to work. does anyone know how i can break it into different rows?
def mail():
sender_email = "xx#gmail.com"
message = MIMEMultipart("alternative")
message["Subject"] = "xx"
message["From"] = sender_email
message["To"] = user_mail
add = '\n'
list = Lines.query.all()
for s in list:
add += str(s.title) + '\r\n'
print(add)
# Write the plain text part
text = "Thank you for submitting a xx! Here are the lines submitted: " + add
# write the HTML part
html = """\
<html>
<head><head style="margin:0;padding:0;">
<table role="presentation" style="width:100%;border-collapse:collapse;border:20;border-spacing:20;background:#cc0000;">
<tr>
<td align="center" style="padding:20;color:#ffffff;">
Your xxxxx was submitted!
</td>
</tr>
</table>
</head>
<p>Thank you for submitting a xx! Here are the lines submitted for your reference:<br><br>
""" + add + """
<br></br>
</p>
</html>
"""
# convert both parts to MIMEText objects and add them to the MIMEMultipart message
part1 = MIMEText(text, "plain")
part2 = MIMEText(html, "html")
message.attach(part1)
message.attach(part2)
...
server.sendmail("xx#gmail.com", user_mail, message.as_string())
return redirect(url_for('complete'))
I believe what you're looking for is this:
list = Lines.query.all()
for s in list:
add += str(s.title) + '<br>'
or (using format vs string concatenation):
list = Lines.query.all()
for s in list:
add += '{}<br>'.format(str(s.title))
or (python 3.6+ f strings):
list = Lines.query.all()
for s in list:
add += f"{s.title}<br>"
\n is not for HTML, but <br> is.
You can use an empty string and keep adding in the loop.
str = ""
for s in list:
str += f"{s.title}\n"

Is it possible to iterate a dict in python for use in a html email

I am trying to send a email notification, and I would like to send dynamic data(for testing purposes my dictionary is static). How ever when I iterate trough my dictionary only one value shows up in the email. Any help would be greatly appreciated!!!
Here is my email.py
import smtplib
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
# me == my email address
# you == recipient's email address
me = "test_email#mydomain.com"
you = "test_email_user#mydomain.com"
msg = MIMEMultipart('alternative')
msg['Subject'] = "Link"
msg['From'] = me
msg['To'] = you
justin = "Justin"
p = {u'Contracts that need signed by: Justin': [[u'/contracts/26203', u'/contracts/26194', u'/contracts/26199', u'/contracts/26173']]}
for a in p.keys():
b = p['Contracts that need signed by: Justin']
for c, d in enumerate(b):
e = d
for f in e:
html = """\
<html>
<head></head>
<body>
<p>Contracts that need signed by """ + justin + """<br>
How are you?<br>
Here is the link you wanted.
</p>
</body>
</html>
"""
part2 = MIMEText(html, 'html')
msg.attach(part2)
s = smtplib.SMTP('localhost')
s.sendmail(me, you, msg.as_string())
s.quit()
Here is the email I get ^
Contracts that need signed by Justin
How are you?
Here is the link you wanted.
Which I want it to look like this
Contracts that need signed by Justin
How are you?
#EACH OF THE LINKS WOULD BE THE NEXT VALUE IN MY DICTONARY.
Here is the link1 you wanted.
Here is the link2 you wanted.
Here is the link3 you wanted.
Here is the link4 you wanted.
You are overwriting the html variable over and over again.
You have to add always 1 line in the for loop like this:
justin = "Justin"
p = {u'Contracts that need signed by: Justin': [[u'/contracts/26203', u'/contracts/26194', u'/contracts/26199', u'/contracts/26173']]}
for a in p.keys():
b = p['Contracts that need signed by: Justin']
for c, d in enumerate(b):
e = d
html = """\
<html>
<head></head>
<body>
<p>Contracts that need signed by """ + justin + """<br>
How are you?<br>
"""
for f in e:
html = html + """Here is the link you wanted. \n"""
html = html + """</p>
</body>
</html>
"""
part2 = MIMEText(html, 'html')
print part2
The problem is you overwrite html variable on each iteration.
You can use string formatting for your problem:
for c, d in enumerate(b):
e = d
html = """\
<html>
<head></head>
<body>
<p>Contracts that need signed by """ + justin + """<br>
How are you?<br>
{0}
</p>
</body>
</html>
"""
s = []
for f in e:
print(f)
s.append('Here is the <a href="http://contract.mydomain.com/{0}>link</a> you wanted.'.format(f))
print(s)
html = html.format('\n'.join(s))
print(html)
output:
<html>
<head></head>
<body>
<p>Contracts that need signed by aaa<br>
How are you?<br>
Here is the <a href="http://contract.mydomain.com//contracts/26203>link</a> you wanted.
Here is the <a href="http://contract.mydomain.com//contracts/26194>link</a> you wanted.
Here is the <a href="http://contract.mydomain.com//contracts/26199>link</a> you wanted.
Here is the <a href="http://contract.mydomain.com//contracts/26173>link</a> you wanted.
</p>
</body>
</html>

Python - sending HTML Mail with Variables

I wanted to make a small cronmailer for my personal use. And here's the part wich do not work
# Create the body of the message (a plain-text and an HTML version).
text = "LOG OUTPUT: " + sys.argv[1] + "\n"
logdata = open(sys.argv[2], "rb")
for row in logdata:
text = text + row
html = """\
<html>
<head></head>
<body>
<p>LOG OUTPUT: {0} <br> {1}
</p>
</body>
</html>
""".format(unicode(str(sys.argv[1]),'utf-8'), unicode(str(logdata),'utf-8'))
part1 = MIMEText(text, 'plain')
part2 = MIMEText(html, 'html')
msg.attach(part1)
msg.attach(part2)
server = smtplib.SMTP(str(server) + ":" + str(port))
server.starttls()
server.login(username,password)
server.sendmail(emailfrom, emailto, msg.as_string())
server.quit()
I get the mail. With the Plain Text and the attachment (left the code out, cause it works). But not the HTML part. The only thing I get there is:
<html>
<head></head>
<body>
<p>LOG OUTPUT: test
Thanks for any help and a Happy New Year
Here are likely-better ways to build that html string (in Python 2):
import cgi
text = "LOG OUTPUT: " + sys.argv[1] + "\n"
with open(sys.argv[2], "rb") as f:
text += f.read()
html = """\
<html>
<head></head>
<body>
<p>LOG OUTPUT: {0}<br/>
<pre>{1}</pre>
</p>
</body>
</html>""".format(unicode(str(sys.argv[1]), 'utf-8'),
unicode(cgi.escape(text), 'utf-8'))
Note that in Python 3 the escaping function is html.escape (so you'd better not name your own variable html as it will clash:-), but for Python 2, where the escaping function is the peculiarly named cgi.escape, this should be OK.

generating emails group by tuple values python

I have a tuple in the format (Name, email, units sold). I would like to generate an HTML table, grouped by Name and then embed that table into an email through Outlook.
My Code:
from itertools import groupby
from operator import itemgetter
import win32com.client
mytuple = [('Andrew','Andrew#gmail.com','20'),('Jim',"Jim#gmail.com",'12'),("Sarah","Sarah#gmail.com",'43'),("Jim","Jim#gmail.com",'15'),("Andrew","Andrew#gmail.com",'56')]
mytuple = sorted(mytuple)
FULL_HTML = []
for name, rows in groupby(mytuple, itemgetter(0)):
table = []
for name, value2 in rows:
table.append(
"<tr><td>{}</td><td>{}</td></tr>".format(
name, value2 ))
html_code = "<html><table>" + str(table) + "</table></html>"
olMailItem = 0x0
obj = win32com.client.Dispatch("Outlook.Application")
newMail = obj.CreateItem(olMailItem)
newMail.Subject = "This is the subject"
newMail.HTMLBody = html_code
newMail.To = "sampleemail#gmail.com"
newMail.Display()
Desired output:
This would open 3 emails with HTML code in their body.
Email 1:
<html>
<table>
<tr><td>Andrew</td><td>20</td><td></tr>
<tr><td>Andrew</td><td>56</td><td></tr>
</table>
</html>
Email 2:
<html>
<table>
<tr><td>Jim</td><td>12</td><td></tr>
<tr><td>Jim</td><td>15</td><td></tr>
</table>
</html>
Email 3:
<html>
<table>
<tr><td>Sarah</td><td>43</td><td></tr>
</table>
</html>
Here's your problem:
for name, value2 in rows:
table.append(
"<tr><td>{}</td><td>{}</td></tr>".format(
name, value2 ))
Change this to:
for n, e, id in rows:
table.append(
"<tr><td>{}</td><td>{}</td></tr>".format(
n, id ))
html_code = "<html><table>" + ''.join(table) + "</table></html>"
The groupby function still returns 3-tuples.

Categories

Resources