3. 发送电子邮件
一个使用数据库的系统,无论是一个web服务还是一个其他的应用系统,都非常有机会需要通过发送邮件的方式和用户交互。如果能够在我们的trigger或者存储过程中直接发送邮件,那么将会是非常的方便。SQL Server给我们提供了很多选择:
1) 自己写一个XP(扩展存储过程)来发送邮件,这将是一件非常令人头疼的事情,你需要了解邮件通信的机制和协议,或者利用一些现成的API和接口来实现你的存储过程。最后写出来的XP也许是一个功能不够强大又非常不稳定的东西。所以对于普通用户,不推荐使用此方法。
2) SQL Mail: 基于MAPI,特点是能够将查询结果和邮件一起发送。但是如果你希望你的程序能够移植到SQL Server 2005以后的版本,那么建议你不要使用它。因为微软已经宣称要从以后的版本中移除这个功能了。
3) Database Mail: SQL Server 2005中的新特性,功能强大,支持通用的SMTP协议,如果你使用的是SQL Server 2005, 那么推荐你使用它。
4) OLE Automation: 利用OLE Automation创建CDO.Message来发送邮件,如果你的数据库版本不支持Database Mail,而且也想通过SMTP灵活的发送邮件,那他它也是一个不错的选择。
SQL Mail
SQL Mail 是基于MAPI的,需要数据库服务器安装有Outlook应用程序。SQL Mail的最大特点就是能够将查询结果作为邮件内容或者附件进行发送。发送SQL Mail使用的存储过程是xp_sendmail。
根据微软的资料,SQL Mail的功能将会在未来的版本中被移除, 而推荐使用的是SQL Server 2005 的Database Mail功能;另外SQL Mail还需要配置Outlook邮件账户,加上本身功能受一定的局限性,因此不推荐使用。
注意:SQL2005中需要从Surface Area Configuration中将SQL Mail选项打开。
定义

• 示例
下面的代码演示如何创建一个账户和一个档案文件,并且降账户分配给Profile(档案文件)。
Profile创建好了,我们就可以利用它来发邮件了。-- 创建邮件账户
EXECUTE msdb.dbo.sysmail_add_account_sp
@account_name = 'MyMailAccount',
@description = 'Mail account for use by all database users.',
@email_address = 'test@sina.com',
@replyto_address = 'test@sina.com',
@display_name = 'Mail Tester',
@mailserver_name = 'stmp.sina.com',
@username = 'test',
@password = 'password' ;
-- 创建邮件用户档案文件
EXECUTE msdb.dbo.sysmail_add_profile_sp
@profile_name = 'MyProfile',
@description = 'Profile used for administrative mail.' ;
-- 将账户加入到档案文件中
EXECUTE msdb.dbo.sysmail_add_profileaccount_sp
@profile_name = 'MyProfile',
@account_name = 'AdventureWorks Public Account',
@sequence_number =1 ;
-- 将访用户档案的权限赋予给msdb数据库的所有用户
EXECUTE msdb.dbo.sysmail_add_principalprofile_sp
@profile_name = 'MyProfile',
@principal_name = 'public',
@is_default = 1 ;
利用OLE Automation 存储过程创建并发送邮件-- 账户配置好以后,我们就可以发送邮件了
EXEC msdb.dbo.sp_send_dbmail
@profile_name = 'MyProfile',
@recipients = 'target@hotmail.com',
@body = 'The stored procedure finished successfully.',
@subject = 'Hello!' ;
注意:SQL2005中需要从Surface Area Configuration中将OLE Automation选项打开
OLE Automation功能使得我们能够象asp一样创建很多基于COM的对象,使SQL的功能得到了很大的扩展。但是在它本身也存在一些缺陷,在SQL Server中对这些对象的属性赋值以及方法调用,都需要通过存储过程间接实现,效率相对低下,并且比较麻烦,不过偶尔用用还是不错的
利用OLE Automation来发送邮件的步骤同样比较繁琐,首先创建一个CDO.Message对象,通过sp_OASetProperty 设置Message对象的各种属性,包括SMTP服务器的信息,还有邮件本身的信息包括标题、正文和收件人等。最后利用sp_OAMethod添加附件,进行发送操作;最后发送完毕后还需要将创建的对象进行删除。总之是非常的麻烦,不过如果将其封装为一个自定义存储过程的话,用起来还是能方便很多的。
• 示例
下面的代码演示了如何通过OLE Automation来发送邮件,为了简化代码,这里没有进行任何错误处理。
declare @iMsg int
-- 创建CDO.Message 对象
EXEC sys.sp_OACreate 'CDO.Message', @iMsg OUT
-- 配置消息对象
--这里我们配置一个远程邮件服务器
EXEC sys.sp_OASetProperty @iMsg, 'Configuration.fields("http://schemas.microsoft.com/cdo/configuration/sendusing").Value', '2'
-- 配置smpt服务器地址和端口.
EXEC sys.sp_OASetProperty @iMsg, 'Configuration.fields("http://schemas.microsoft.com/cdo/configuration/smtpserver").Value', '127.0.0.1'
EXEC sys.sp_OASetProperty @iMsg, 'Configuration.fields("http://schemas.microsoft.com/cdo/configuration/smtpserverport").Value', 25
-- Save the configurations to the message object.
EXEC sys.sp_OAMethod @iMsg, 'Configuration.Fields.Update', NULL
-- Set the e-mail parameters.
EXEC sys.sp_OASetProperty @iMsg, 'MimeFormatted', FALSE
EXEC sys.sp_OASetProperty @iMsg, 'To', 'receiver@hotmail.com'
EXEC sys.sp_OASetProperty @iMsg, 'Subject', 'Hello!'
EXEC sys.sp_OASetProperty @iMsg, 'TextBody', 'This is an Email from SQL Server!'
--send the mail
EXEC sys.sp_OAMethod @iMsg, 'Send', NULL
-- 清除创建的对象.
EXEC sys.sp_OADestroy @iMsg