在2004年秋,软件在世界的因特网发展内介绍: 因特网ADO.Net Provider。 一些最通常使用来自受欢迎的IP *的物体工作! 工具箱包括一新产品叫IP *Works! ADO.Net Provider,允许你用一种方式即数据库开发者更熟悉用这些协议工作。 为了从你的收件箱收到所有邮件,你能选择 SELECT * from INBOX。 读最新的RSS 你能SELECT * from feed。 为了发电子邮件,insert a new row into the OUTBOX table。
在这篇文章里, 我将谈论Provider的特征和使用, 并且沿着路我将建立有能力的Webmail与最小数量的代码接口的IMAP 和POP。 你也能这里下载充分的样品工程。
Provider的概述
在开始过程中,可得到的协议是IMAP,POP,SMTP,NNTP 和RSS。 其它人将被增加,象WebDAV(又名HTTPMail),LDAP,等一样。 IP *Works! ADO.Net 数据Provider使因特网能力进入应用迅速和容易 - 没有需要自己熟悉协议的内部运转。
你熟悉DbConnection,DbDataAdapter 和DbCommand 物体。 现在让我介绍IPWorksConnection,IPWorksDataAdapter 和IPWorksCommand 物体。 除了用在里面上发生的不同一点的某些事情,他们按相同熟悉方式工作 - 从一台服务器不断改进而不是数据库。 这是在Provider里的不同的物体的简短描述。 过后在这篇文章里我将陷入更多的细节并且显示怎样使用每一个。
IPWorksConnection
IPWorksConnection 物体管理对一些服务器的一个Connection,不管它是IMAP,POP,HTTP,SMTP或者NNTP服务器。 IPWorksConnection可以被明确地启闭,或者IPWorksDataAdapter可以管理自动(只有当必要时打开)Connection。
IPWorksDataAdapter
IPWorksDataAdapter正如你习惯于的DataAdapter一样。 它将允许你执行命令居住于DataSet或者DataTable。 如果一个Connection不公开,为了进行必要手术,一个人将被自动建立。
IPWorksCommand
IPWorksCommand对象描述一个SQL命令: 选择,插入,删除,或者不断改进。
IPWorksCommandBuilder
IPWorksCommandBuilder对象将自动产生插入,删除,并且不断改进适合IPWorksDataAdapter的命令,给一条确定的选择命令。
Connection
首先,开始我将安装IPWorksConnection,因此我需要确定这Connection线。 为了形成这根Connection线,仅仅指定所有Connection的特性当半冒号分开价值时。 一Connection特性被在IPWorksConnection的全部实例里要求: 协议 . 协议Connection财产指定要为这个Connection使用的网际协议。 取决于协议,其他Connection特性将申请。 例如,如果我使用IMAP 协议,为了连结,我将需要指定mailserver,用户和密码特性。 如果我使用RSS 协议,我将至少需要URL。 这是一些例子:
ipWorksConnection ipwConnection1 = new ipWorksConnection("protocol=imap;
mailserver=myserver; user=myusername; password=mypassword");
ipWorksConnection ipwConnection2 = new ipWorksConnection("protocol=rss;
url=http://slashdot.org/");
ipWorksConnection ipwConnection3 = new ipWorksConnection("protocol=nntp;
newsserver=msnews.microsoft.com");
ipWorksConnection ipwConnection4 = new ipWorksConnection("protocol=smtp;
mailserver=myserver");
ipWorksConnection ipwConnection5 = new ipWorksConnection("protocol=pop;
mailserver=myserver; user=myusername; password=mypassword");
一Connection线特性的全部目录,请请教给IP *的文档编制工作! ADO.Net 数据Provider。
我的目标是建立webmail 应用 - 因此我的Connection线将需要在用户能指定他们的用户名,密码,等等的地方接受一个网形式的价值 我的connectionstring 将如此看起来象:
ipWorksConnection1 = new ipWorksConnection(String.Format("protocol={0};
mailserver={1}; user={2}; password={3};",
rblProtocol.SelectedItem.Value, txtServer.Text,
txtUser.Text, txtPass.Text));
专栏
对下一步来说,我将建立一名数据改编者,并且使它的命令成形:
ipWorksDataAdapter ipworksDataAdapter1 = new ipWorksDataAdapter();
当执行那命令时,每命令将与应该被使用的一个Connection有关。 对webmail 应用来说,我需要能选择使用一个IMAP Connection和一个POP Connection。 自从我的Connection线允许用户选择是使用IMAP 还是POP, 我只需要保证我的选择命令将对两者中任何一个有效。 每份协议有它有效的专栏和Tables的自己的目录。
例如,POP 协议支持下列专栏:
messageid
messagefrom
messagesubject
messagetext
messagedate
messagecc
messageheaders
messagereplyto
messagesize
messageto
IMAP,作为一份更有特色的协议,支持更多的专栏。 除由上面的POP 提供的所有那些之外,IMAP也提供下列专栏:
messageflags
messagedeliverytime
messagesender
messagebcc
messageinreplyto
messagenetid
messagecontenttype
messagecontentencoding
为了使相同的选择陈述为两份协议中的任一份工作,我只将把我自己限制在被两份协议支持的那些专栏。 选择,我使用不同选择陈述能取决于那些协议,或者我使用能一选择 * 得到所有柱子。
ipWorksDataAdapter1.SelectCommand = new ipWorksCommand("SELECT messageid,
messagefrom, messagesubject, messagedate, messagesize FROM INBOX",
ipWorksConnection1);
Tables
上述选择命令从收件箱Tables得到一些柱子。 但是什么其他Tables是可提供的? 可得到的Tables取决于协议。 对POP 来说,收件箱是那里的唯一的Tables。 类似RSS只有一张Tables(供给本身)。 但是为象IMAP 和NNTP一样的其他协议,有多张Tables。
对IMAP 协议来说,Tables仅仅是你感兴趣的IMAP 信箱(文件夹)的名字。 因此收件箱通常为POP 和IMAP工作, 但是再次IMAP在POP 上方有附加能力, 因此如果你的IMAP收件箱有一本附属称为"ToDo"的文件夹,你也将有一张"INBOX.ToDo"Tables。
一张特别的Tables,"SchemaTables",能用来得到一张Tables名字的Tables。 这将用IMAP 协议得到一个所有信箱文件夹的目录有用, 在NNTP得一个所有关于一个特别的新闻菜盘有时间的组织的目录。 为了使用schemaTables,你将使用以下的选择陈述:
"SELECT * FROM INFORMATION_SCHEMA.TABLES"
充满一张数据表
为了这篇文章,我将为了把收件箱Tables用于POP 和IMAP 粘住。 在这点,我们几乎处理基础。 我们有一个Connection,有一条选择命令的一名改编者。 所有的左边将用结果充满一张Tables。
ipWorksConnection1 = new ipWorksConnection(String.Format("protocol={0};
mailserver={1}; user={2}; password={3};",
rblProtocol.SelectedItem.Value, txtServer.Text,
txtUser.Text, txtPass.Text));
ipWorksDataAdapter ipworksDataAdapter1 = new ipWorksDataAdapter();
ipWorksDataAdapter1.SelectCommand = new ipWorksCommand("SELECT messageid,
messagefrom, messagesubject, messagedate, messagesize FROM INBOX",
ipWorksConnection1);
System.Data.DataTable dataTable1 = new System.Data.DataTable();
ipWorksDataAdapter1.Fill(dataTable1);
Webmail - 登录
在这webmail 应用里 - 我大约网络通信(IMAP,POP,SMTP)不必非常认为,我将使用*Works的IP! ADO.Net Provider。 我确实必须考虑会议管理和数据赠送。 我需要提供一个注册号机制,因此我将把一个形式验证部分增加到web.config:
<authentication mode="Forms">
<forms name="Login" loginUrl="login.aspx" />
</authentication>
然后我将实现注册号形式(login.aspx)。 注册号形式将包含textBoxes 用户进入必要用户,密码和服务器信息。 它也将包含radioButtonList选择POP 或者IMAP 和当然一枚"登录"钮扣。 当这枚注册号钮扣被点击时,一个ipWorksConnection 物体将被使用用户输入建立。
当我使用ipWorksDataAdapter时,当它被要求时,它能自动打开一个Connection,而不是我保持Connection开。 但是, 既然用户将用postbacks在会议的一生交往, 用户一登录,我就通过给会议添加ipWorksConnection 实例保持Connection, 并且手工打开它,为了保持它开,直到会议结束或者直到用户注销。
RedirectFromLoginpage背在我们是的结果在哪里的URL(例如,default.aspx)最后,在所有这我之后将。
private void bLogin_Click(object sender, System.EventArgs e)
{
ipWorksConnection1 = new IPWorksConnection(String.Format("protocol={0};
mailserver={1}; user={2}; password={3};",
rblProtocol.SelectedItem.Value, txtServer.Text,
txtUser.Text, txtPass.Text));
Session.Clear();
try
{
ipWorksConnection1.Open();
Session.Add("IPWorksConnection", ipWorksConnection1);
FormsAuthentication.RedirectFromLoginPage(txtUser.Text, false);
}
catch (Exception ex)
{
lError.Text = ex.Message;
}
}
浏览电子邮件
在default.aspx里,我将使用datagrid在这个收件箱里展示电子邮件。 在页里 _ 很多这主页,我将检查看看是否在会议上有一个dataView 物体。 如果这不在那里, 我知道那个这第一次是这几次会议被记录进,并且我执行这几次会议一些去安装的措施将:
造成一个ipWorksConnection 实例并且设置它等于在会议(被在login.aspx里建立)里的那个。
创建ipWorksDataAdapter 和选择命令选择我想要的消息专栏。
用ipWorksDataAdapter充满DataTable。
确定一个等于新近充满的DataTable的缺省观看的dataView 物体,并且给会议添加新dataView。
dataView已经在会议内存在如果,我知道不执行这些步,并且databind的实在的改为datagrid。
private void Page_Load(object sender, System.EventArgs e)
{
DataView dv = (DataView)Session["MessageView"];
if (dv == null)
{
DataTable dt = new DataTable();
IPWorksConnection dataConnection =
(IPWorksConnection)Session["IPWorksConnection"];
IPWorksDataAdapter dataAdapter = new IPWorksDataAdapter();
dataAdapter.SelectCommand = new IPWorksCommand("SELECT messageid,
messagefrom, messagesubject, (DateTime)messagedate,
(int)messagesize FROM INBOX", dataConnection);
dataAdapter.Fill(dt);
dv = dt.DefaultView;
Session.Add("MessageView", dv);
}
dgMessages.DataSource = dv;
dgMessages.DataBind();
}
赠送
在这点,用户已经登录并且有边界的datagrid包括有关电子邮件的信息。 注意到使用的选择陈述只得到messageid,messagefrom,messagesubject,messagedate 和messagesize。 我没选择messagetext。 这最好是真实消息身体的内容可能巨大(如果说在那里大附件,或者很多电子邮件的实在)。 在一个用户已经点击一条特别的消息之后,我将改为只选择messagetext。
建立一种方式一个用户点击一条消息, 我将使的一些datagrid HyperLink 柱子的柱子,格式化超链接创造包括他们已经点击的消息的messageID。 例如,主题专栏正文价值将被绑在"messagesubject"专栏上,但是它的URL 领域将是"messageid"。 URL 形式柱子的线将"read.aspx吗? uid = {0 }". 这给我们做这个专栏的正文进与read.aspx的联系的能力, uid querystring 易变的价值将来自被选择的排的messageid 柱子。 我当然地做能相同有从,日期,和/或尺寸柱子被如此想要。
读电子邮件
read.aspx 包含将形式显示内容的那些电子邮件,和这重要报文首部象一样从,给,主题,等等
在页里面 _ 装,我选择那些柱子将完全从以前,除这messagetext 柱子之外。 这次,我将象如此一样使用地点条款选择只那些柱子从messageid在querystring内通过的一个人在哪里的排那里:
private void Page_Load(object sender, System.EventArgs e)
{
IPWorksConnection dataConnection =
(IPWorksConnection)Session["IPWorksConnection"];
IPWorksDataAdapter dataAdapter = new IPWorksDataAdapter();
dataAdapter.SelectCommand = new IPWorksCommand("SELECT messageid,
messagefrom, (String)messageto, messagesubject,
(DateTime)messagedate, (int)messagesize, messagetext FROM INBOX
WHERE messageid = " + Request.QueryString["uid"], dataConnection);
dataAdapter.Fill(dt);
this.DataBind();
}
在设计时间内,我有界限正文textBoxes的特性在形式与他们各自柱子在DataTable内上。 在命名txtMessage,我在包含消息身体的内容的表格上设置哪个的textBox的databindings内, 我确定风俗捆正文财产给dt.Rows的表示 [0]["messagetext" ]. 我也将在这个形式(lSubject,lTo,lFrom,等等)上确定其它标签的databindings。 以这种方法,我一在页里叫DataBind _ 装,所有控制价值将从DataTable那里自动居住。
databinding以来那些lSize 标签,我把它和称为FormatSize的功能结合起来将(在这messagesize 专栏内度过估价)改为。 以这种方法用毫巴,Kb或者只不过字节我能格式化尺寸正文。
public static string FormatSize(object o)
{
int i = Convert.ToInt32(o);
string[] suffix = {"b","kb", "mb", "gb"};
int j = 0;
while (i > 1024 && j < 4)
{
i = i / 1024;
j++;
}
return (i + " " + suffix[j]);
}
组成邮件
发电子邮件,并且关于DataTable 考虑那 - 寄一个新邮件自然跟随那,你应该插入一新排。
对刚刚创造一新ipWorksCommand宾语,打开Connection,并且叫ipWorksCommand 物体ExecuteReader 方法这样做的一种方法。 使用插入物命令, 确定参数系列命令目的给他们的各自的栏目名从插入物那里命令自己的与相配的价值是必要的, 象在下面的例子里一样:
private void bSend_Click(object sender, System.EventArgs e)
{
IPWorksConnection dataConnection = new IPWorksConnection(
String.Format("protocol=smtp; mailserver={0};",
getConnParam("mailserver")));
try
{
IPWorksCommand ipWorksCommand1 = new IPWorksCommand("INSERT INTO outbox
(sendto, subject, messagetext, messagefrom)", dataConnection);
((IDataParameter)ipWorksCommand1.Parameters[0]).Value = txtTo.Text;
((IDataParameter)ipWorksCommand1.Parameters[1]).Value = txtSubj.Text;
((IDataParameter)ipWorksCommand1.Parameters[2]).Value = txtMsg.Text;
((IDataParameter)ipWorksCommand1.Parameters[3]).Value = txtFrom.Text;
dataConnection.Open();
ipWorksCommand1.ExecuteReader();
}
catch (Exception ex)
{
lError.Text = ex.Message;
}
finally
{
dataConnection.Close();
}
}